Problem:
Score : 400 points

Problem Statement

Give a pair of integers (A, B) such that A^5-B^5 = X.
It is guaranteed that there exists such a pair for the given integer X.

Constraints

1 \leq X \leq 10^9

X is an integer.

There exists a pair of integers (A, B) satisfying the condition in Problem Statement.

Input

Input is given from Standard Input in the following format:

X

Output

Print A and B, with space in between.
If there are multiple pairs of integers (A, B) satisfying the condition, you may print any of them.

A B

Sample Input 1

33

Sample Output 1

2 -1

For A=2 and B=-1, A^5-B^5 = 33.

Sample Input 2

1

Sample Output 2

0 -1

Solution in Rust (1.42.0) (judge verdict: Accepted)

/* #region template */
#![allow(unused_imports)]
use std::cmp::{max, min};
use std::io::{stdin, stdout, Bytes, Read, Stdin, StdinLock, Stdout, StdoutLock, Write};
use std::iter::{repeat, repeat_with};
use std::mem::swap;
use std::str::FromStr;
#[allow(dead_code)]
struct Io<'a> {
    reader: Bytes<StdinLock<'a>>,
    writer: StdoutLock<'a>,
    in_buf: [u8; BUF_SIZE],
}
#[allow(dead_code)]
impl<'a> Io<'a> {
    fn new(stdin: &'a Stdin, stdout: &'a Stdout) -> Io<'a> {
        Io {
            reader: stdin.lock().bytes(),
            writer: stdout.lock(),
            in_buf: [0; BUF_SIZE],
        }
    }
    fn r<T: FromStr>(&mut self) -> T {
        let mut count = 0;
        loop {
            match self.reader.next() {
                Some(Ok(b' ')) | Some(Ok(b'\n')) => break,
                Some(Ok(c)) => self.in_buf[count] = c,
                _ => panic!(),
            }
            count += 1;
        }

        let s = unsafe { std::str::from_utf8_unchecked(&self.in_buf[0..count]) };
        s.parse().unwrap_or_else(|_| panic!())
    }
    fn ru(&mut self) -> usize {
        self.r()
    }
    fn iter<'b, T>(&'b mut self) -> IoIter<'a, 'b, T> {
        IoIter::new(self)
    }
    fn c<T: FromStr>(&mut self, n: usize) -> Vec<T> {
        self.iter().take(n).collect()
    }
    fn cu(&mut self, n: usize) -> Vec<usize> {
        self.c(n)
    }
    fn w<T: std::fmt::Display>(&mut self, v: T) {
        writeln!(self.writer, "{}", v).unwrap();
    }
    fn wn<T: std::fmt::Display>(&mut self, v: T) {
        write!(self.writer, "{}", v).unwrap();
    }
}
#[allow(dead_code)]
struct IoIter<'a: 'b, 'b, T> {
    io: &'b mut Io<'a>,
    m: std::marker::PhantomData<T>,
}
#[allow(dead_code)]
impl<'a: 'b, 'b, T> IoIter<'a, 'b, T> {
    fn new(io: &'b mut Io<'a>) -> IoIter<'a, 'b, T> {
        IoIter {
            io,
            m: std::marker::PhantomData,
        }
    }
}
impl<'a, 'b, T: FromStr> Iterator for IoIter<'a, 'b, T> {
    type Item = T;
    fn next(&mut self) -> Option<Self::Item> {
        Some(self.io.r())
    }
}
fn main() {
    let stdin = stdin();
    let stdout = stdout();
    let mut io = Io::new(&stdin, &stdout);
    unsafe {
        solve(&mut io);
    }
}
/* #endregion */

const BUF_SIZE: usize = 1024;

unsafe fn solve(io: &mut Io) {
    let x: i128 = io.r();
    for i in 1..(x as f64).sqrt() as i128 + 1 {
        if x % i == 0 {
            check(x, i, io);
            if i != x / i {
                check(x, x / i, io);
            }
        }
    }
    unreachable!();
}

fn check(x: i128, i: i128, io: &mut Io) {
    let mut a = i / 2;
    let mut b = a - i;

    while check2(x, a, b, io) {
        a += 1;
        b += 1;
    }
}

fn check2(x: i128, a: i128, b: i128, io: &mut Io) -> bool {
    let res = (a - b) * (a.pow(4) + a.pow(3) * b + a.pow(2) * b.pow(2) + a * b.pow(3) + b.pow(4));
    if res == x {
        io.wn(a);
        io.wn(' ');
        io.w(b);
        std::process::exit(0);
    } else if res > x {
        false
    } else {
        true
    }
}