def test_others(): resolver = ExpressionResolver(verbose=False) ret = resolver.solve(expression="0 = X + X") assert ret == "0.0" ret = resolver.solve(expression="0 = X ^ 2 + X^ 2") assert ret == "0.0"
def main(argv=None): print() parser = argparse.ArgumentParser() parser.add_argument("expression", type=str, help="Insert expression to resolve.") parser.add_argument( "-v", "--verbose", help="Add verbose and print different resolving step.", action="store_true", ) parser.add_argument( "-vv", "--force_calculator_verbose", help="Add all verbose and force the calculator verbose.", action="store_true", ) args = parser.parse_args(argv) resolver = ExpressionResolver( verbose=args.verbose | args.force_calculator_verbose, force_calculator_verbose=args.force_calculator_verbose, ) try: result = resolver.solve(args.expression) if isinstance(result, list): print("The ", len(result), " solutions are :") for res in result: print(res) else: print("result = ", result) except SyntaxError as e: print("The expression syntax is not accepted : ", e) except ValueError as e: print("One of the value in the expression is not accepted : ", e) except NotImplementedError as e: print("One of the methods needed is not implemented yet : ", e) except NothingToDoError as e: print(e) except Exception as e: print("An exception appened : ", e)
def test_equations_infinite_solution(): resolver = ExpressionResolver(verbose=False) # Numbers only ret = resolver.solve(expression="2 = 2") assert ret == "X can be any real number." ret = resolver.solve(expression="5 * X^0 = 5 * X^0") assert ret == "X can be any real number." ret = resolver.solve(expression="4 * X^0 = 8") assert ret == "There is no solution for this equation." # Float only ret = resolver.solve(expression="2.2456 = 2.2456") assert ret == "X can be any real number."
def test_equation_subject(): resolver = ExpressionResolver(verbose=False) ret = resolver.solve(expression="5 * X^0 + 4 * X^1 - 9.3 * X^2 = 1 * X^0") assert ret == ["-0.475131", "0.905239"] ret = resolver.solve(expression="5 * X^0 + 4 * X^1 = 4 * X^0") assert ret == "-0.25" with pytest.raises(NotImplementedError) as e: ret = resolver.solve( expression="8 * X^0 - 6 * X^1 + 0 * X^2 - 5.6 * X^3 = 3 * X^0") assert ( str(e.value) == "The polynomial degree is strictly greater than 2, the resolver is not implemented yet." ) ret = resolver.solve(expression="5 + 4 * X + X^2= X^2")
def test_any_calc(): resolver = ExpressionResolver(verbose=False) calculator = _Calculator() with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression=" (5 + 2y)(2 - (2y * 3y))") assert str(e.value) == "Var cannot be inside a parenthesis for the moment." ret = resolver.solve(expression="y[5 + 2](2 - {2 * -3.54]]") assert ret == "63.56*Y" ret = resolver.solve(expression="5y/y") assert ret == "5.0" with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression=" -5 - 4 * X + X^2= X^2 + x^5") assert ( str(e.value) == "The polynomial degree is strictly greater than 2, the resolver is not implemented yet." )
def test_wrong_args(): resolver = ExpressionResolver(verbose=False) # Wrong args with pytest.raises(SyntaxError) as e: resolver.solve(expression="6&7-2") assert str( e.value ) == "This is not an expression or some of the operators are not reconized." # Sign without value after with pytest.raises(SyntaxError) as e: resolver.solve(expression="4^0-") assert str( e.value ) == "Operators or sign must be followed by a value or a variable." # Operator wrong syntax with pytest.raises(SyntaxError) as e: resolver.solve(expression="42//5") assert ( str(e.value) == "Operators must be followed by a value or a variable, not another operator." ) # More than one = in the expression with pytest.raises(NotImplementedError) as e: resolver.solve(expression="42 * X = 42 * Y = 42 * Z") assert str( e.value) == "More than one comparison is not supported for the moment." # lot of sign and operator between with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="4^+-+^++-0 = 0") assert ( str(e.value) == "Operators must be followed by a value or a variable, not another operator." ) # multiple comma in one number with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="450.25.45 + 12") assert str(e.value) == "Some numbers are not well formated : 450.25.45" # wrong use of comma with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="450. + 12") assert str(e.value) == "Some numbers are not well formated (Comma error)." # wrong use of comma with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression=".45 + 12") assert str(e.value) == "Some numbers are not well formated (Comma error)." # Sign before operator with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="45 + * 12") assert ( str(e.value) == "Operators must be followed by a value or a variable, not another operator." ) # Test sign before closing parenthesis with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * (5 +)10") assert ( str(e.value) == "Operators must be followed by a value or a variable, not another operator." ) # Test operator before closing parenthesis with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * (5 *)10") assert ( str(e.value) == "Operators must be followed by a value or a variable, not another operator." ) # Test BIGGER than float input with pytest.raises(ValueError) as e: ret = resolver.solve( expression= "-X ^ 3 * 10X ^ 4+ x ^ 2 +x - x ^4 + X ^ 3 - X^1209349432411111115555555555555555555558888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444 - X" ) assert str( e.value ) == "A number is too big, no input number should reach float inf or -inf." # Test BIGGER than float input with pytest.raises(ValueError) as e: ret = resolver.solve( expression= "-X ^ 3 * 10X ^ 4+ x ^ 2 +x - x ^4 + X ^ 3 - 1209349432411111115555555555555555555558888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888888444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444444 - X" ) assert str( e.value ) == "A number is too big, no input number should reach float inf or -inf."
def test_expression_parser(): resolver = ExpressionResolver(verbose=False) # Test sign before var ret = resolver.solve(expression="+X = 10") # Test sign before var ret = resolver.solve(expression="-X = 10") # Test sign before var ret = resolver.solve(expression="-X") # Test sign before var ret = resolver.solve(expression=" +X") # Test addition with sign before var ret = resolver.solve(expression="+X = -x") # lot of sign ret = resolver.solve(expression="4-+-2 ------+-----++++++2") # lot of sign ret = resolver.solve(expression="4-+-2 *+-+++- 0") # Extra zero ret = resolver.solve(expression="04578 + 000450") assert ret == "5028.0" # Test method _replace_zero_power_by_one ret = resolver.solve(expression="04578 + 15000 ^0") assert ret == "4579.0" # Test method _replace_zero_power_by_one, the following one shouln't proc because it use a parenthesis ret = resolver.solve(expression="04578 + (15000 * 450)^0") assert ret == "4579.0" # Test replacing sign before numbers ret = resolver.solve(expression="-4 + (+15 * -45)-0") # Test with var ret = resolver.solve(expression="X ^ 2 + X ^ 1 + x ^ 2") assert ret == "2.0X^2.0+X" # Test with var ret = resolver.solve(expression="X ^ 2 + x + x") assert ret == "2.0X+X^2.0" # Test with var ret = resolver.solve(expression="X ^ 2 + x + x + x ^2") assert ret == "2.0X^2.0+2.0X" # Test with var ret = resolver.solve(expression="X ^ 2 + x + x - x ^2") assert ret == "2.0X" # Test with var ret = resolver.solve(expression="X ^ 2 + x + x - x ^2 - x") assert ret == "X"
def test_equation_degree_two(): resolver = ExpressionResolver(verbose=False) ret = resolver.solve(expression="x^2+x-2 = 0") assert ret == ["1.0", "-2.0"] ret = resolver.solve(expression="x^2+3x+2=0") assert ret == ["-1.0", "-2.0"] ret = resolver.solve(expression="x ^2 + x + 1 = 0") assert ret == ["-0.5+0.866026*i", "-0.5-0.866026*i"] ret = resolver.solve(expression="4x ^2 + 4x + 1 = 0") assert ret == "-0.5" ret = resolver.solve(expression="-x ^2 + 2x - 3 = 0") assert ret == ["1.0-1.414214*i", "1.0+1.414214*i"] ret = resolver.solve(expression="x ^2 + 4x = 0") assert ret == ["0.0", "-4.0"] ret = resolver.solve(expression="x ^2 -2x + 1 = 0") assert ret == "1.0" ret = resolver.solve(expression="x ^ 2 + 1= 0") assert ret == ["i", "-i"] ret = resolver.solve(expression="x^2 -4x + 4 -1= 0") assert ret == ["3.0", "1.0"] ret = resolver.solve(expression="X ^ 2 + X ^1 + x ^2 = 0") assert ret == ["0.0", "-0.5"] ret = resolver.solve(expression="X ^ 2 + X ^1 - x ^2 = 0") assert ret == "0.0" ret = resolver.solve(expression="-X ^ 2 + X ^1 + x ^2 = 0") assert ret == "0.0" ret = resolver.solve(expression="-X ^ 2 + X ^1 - x ^2 = 0") assert ret == ["0.0", "0.5"] ret = resolver.solve(expression="X ^ 2 + X ^1 + x ^1 = 0") assert ret == ["0.0", "-2.0"] ret = resolver.solve(expression="X ^ 2 - X ^1 + x ^1 = 0") assert ret == "0.0" ret = resolver.solve(expression="X ^ 2 - X ^1 - x ^1 = 0") assert ret == ["2.0", "0.0"] # 0 coeff ret = resolver.solve(expression="0x^2 =0") assert ret == "X can be any real number." ret = resolver.solve(expression="0x^2 * X^1 10X^0 =0") assert ret == "X can be any real number." ret = resolver.solve(expression="0x^2 * X^1 + 10X^0 =0") assert ret == "There is no solution for this equation." ret = resolver.solve(expression="0x^2 + X^1 + 10X^0 =0") assert ret == "-10.0" ret = resolver.solve(expression="-0x^2 + X^1 + 10X^0 =0") assert ret == "-10.0" ret = resolver.solve(expression="-0x^2 - X^1 + 10X^0 =0") assert ret == "10.0" ret = resolver.solve(expression="-x^2 - 0X^1 + 10X^0 =0") assert ret == ["-3.162278", "3.162278"] ret = resolver.solve(expression="-x^2 - -0X^1 + 10X^0 =0") assert ret == ["-3.162278", "3.162278"] ret = resolver.solve(expression="-x^2 - -0X^1 -0X^0 =0") assert ret == "0.0" ret = resolver.solve(expression="-0x^2 - -0X^1 -0X^0 =0") assert ret == "X can be any real number." # positive discriminant ret = resolver.solve( expression="5 * X^0 + 13 * X^1 + 3 * X^2 = 1 * X^0 + 1 * X^1") assert ret == ["-0.367007", "-3.632993"] # Zero discriminant ret = resolver.solve( expression="6 * X^0 + 11 * X^1 + 5 * X^2 = 1 * X^0 + 1 * X^1") assert ret == "-1.0" # Negative discriminant ret = resolver.solve( expression="5 * X^0 + 3 * X^1 + 3 * X^2 = 1 * X^0 + 0 * X^1") assert ret == ["-0.5+1.040833*i", "-0.5-1.040833*i"]
def test_equation_degree_one(): resolver = ExpressionResolver(verbose=False) ret = resolver.solve(expression="5 * X^0 + 4 * X^1 = 41 * X^0") assert ret == "9.0" ret = resolver.solve( expression= "-51516544 * X^0 + 4241.1 * X^1 + 1213545 = ---41 * X^0 + -X^1") assert ret == "11858.032106739585" ret = resolver.solve(expression="X ^1 = X ^ 1") assert ret == "X can be any real number." ret = resolver.solve(expression="X = X") assert ret == "X can be any real number." ret = resolver.solve(expression="X^0 = X^0") assert ret == "X can be any real number." ret = resolver.solve(expression="-0x^2 - -X^1 -0X^0 =0") assert ret == "0.0" # Multiplier small after var ret = resolver.solve(expression=" X*0.001=0.000001") assert ret == "0.001" ret = resolver.solve(expression=" X*0.001=-0.000001") assert ret == "-0.001" ret = resolver.solve(expression="5 * X^0 = 4 * X^0 + 7 * X^1") assert ret == "0.14285714285714285"
def test_wrong_equation(): resolver = ExpressionResolver(verbose=False) # Numbers only false ret = resolver.solve(expression="2 = -2") assert ret == "The equation is False." # Numbers with var^0 false ret = resolver.solve(expression="2*X^0 = -2*X^0") assert ret == "There is no solution for this equation." # Float only false ret = resolver.solve(expression="2.2456 = -2.2456") assert ret == "The equation is False." # power var with negative value with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="2 = -2X^-5") assert str( e.value) == "Some part of the polynomial var have negative power." # power var with negative value with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="2 = -2X^(-5)") assert str( e.value) == "Some part of the polynomial var have negative power." # power var with irrational value with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="2 = -2X^5.00000005") assert str(e.value) == "irrational numbers are not accepted as exponent." # power var with negative irrational value with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="2 = -2X^-5.00000005") assert str( e.value) == "Some part of the polynomial var have negative power." # power var with negative irrational value with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="2 = -2X^((-5.00000005))") assert str( e.value) == "Some part of the polynomial var have negative power." with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="x^3 + 2x^2 -3x = 0") assert ( str(e.value) == "The polynomial degree is strictly greater than 2, the resolver is not implemented yet." ) # Nothing left with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression=" =0") assert str( e.value) == "The equation is not well formated. No left or right part."
def test_calculator(): resolver = ExpressionResolver(verbose=False) # Simple test ret = resolver.solve(expression="5 * 5^0") assert ret == "5.0" # Simple test exponential ret = resolver.solve(expression="5 * 5^10") assert ret == "48828125.0" # Simple test with priority ret = resolver.solve(expression="5 * 5 + 10") assert ret == "35.0" # Simple test with float ret = resolver.solve(expression="5.3 * 5.2 + 10.8") assert ret == "38.36" # Test with parenthesis ret = resolver.solve(expression="5 * (5 + 10)") assert ret == "75.0" # Test with multiple parenthesis ret = resolver.solve(expression="5 * (5 + (10 * 50 + 2))") assert ret == "2535.0" # Test with multiple useless parenthesis ret = resolver.solve(expression="((((5 * (5 + (10 * 50 + 2))))))") assert ret == "2535.0" # Hard test with multiple parenthesis ret = resolver.solve( expression= "5 * (5 + (10 * 50 + 24.15) * 50 * 18 *(12 + 52)) * (18 - (5 + 2))") assert ret == "1660507475.0" # Hard test with float ret = resolver.solve( expression="545875785748.34444444478 * 5.2542 + 10456.81212") assert my_round(float(ret), 2) == my_round(2868140563935.763, 2) # Implicit multiplication with open parenthesis ret = resolver.solve(expression="25(5 + 2)") assert ret == "175.0" # Implicit multiplication with closing parenthesis ret = resolver.solve(expression="(5 + 2)25") assert ret == "175.0" # Test different parenthesis ret = resolver.solve(expression="(5 + 2]25") assert ret == "175.0" # Test different parenthesis ret = resolver.solve(expression="[5 + 2]25") assert ret == "175.0" # Test different parenthesis ret = resolver.solve(expression="[5 + 2}25") assert ret == "175.0" # Test multiplying by a signed number ret = resolver.solve(expression="5 * -10 + 599") assert ret == "549.0" # Test multiplying by a signed number ret = resolver.solve(expression="5 * +10") assert ret == "50.0" # Test multiplying by a signed number in parenthesis ret = resolver.solve(expression="5 * (+10)") assert ret == "50.0" # Test multiplying by a signed number in parenthesis ret = resolver.solve(expression="(+10)10") assert ret == "100.0" # Test substract by a signed number in parenthesis ret = resolver.solve(expression="(-10)-10") assert ret == "-20.0" # Test substract by a signed number in parenthesis ret = resolver.solve(expression="(-10)(-10)") assert ret == "100.0" # Test multiplying by a signed float ret = resolver.solve(expression="5 * -10.35843958432134 + 599") assert my_round(float(ret), 2) == my_round(547.2078020783933, 2) # Test sign before first number ret = resolver.solve(expression="-42-2") assert ret == "-44.0" # Test one var with parenthesis in calculator ret = resolver.solve(expression="5 * x(5 + 10)") assert ret == "75.0*X"
def test_calculator_wrong_args(): resolver = ExpressionResolver(verbose=False) # Test with wrong parenthesis number with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * (5 + (10 * 50 + 2)") assert str(e.value) == "Problem with parenthesis." # Test with wrong parenthesis number with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * (5 + (10 * 50 + (2))") assert str(e.value) == "Problem with parenthesis." # Test with right parenthesis number but not good open/close order with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * (5)10 * 50 + )2()(") assert str(e.value) == "Closing parenthesis with no opened one." # Test with right parenthesis number but not good open/close order with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 + (5 + 10) + 2)(15*2") assert str(e.value) == "Closing parenthesis with no opened one." # Test two var in calculator with pytest.raises(SyntaxError) as e: ret = resolver.solve(expression="5 * x(5 + 10) * y") assert str(e.value) == "Calculator does not accept more than 1 var." # Test wrong operation for vars with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="5 * x% 2") assert str( e.value ) == "This type of operation with vars is not accepted for the moment." # Test wrong operation for vars with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="5 * x% x") assert str( e.value ) == "This type of operation with vars is not accepted for the moment." # Test calc with var, var in simple parenthesis with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="-5 - (2thisisavar(2(2+5)) * -1)") assert str(e.value) == "Var cannot be inside a parenthesis for the moment." # Test calc with var, dividing number by a var with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="50 / x * x + (5 * 2)") assert str(e.value) == "Cannot divide a number by a var for the moment." # Test calc with var, power var by var with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="50x^X") assert str(e.value) == "Cannot power a var by a var for the moment." # Test calc with var, power number by var with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="50^X") assert str(e.value) == "Cannot power a number by a var for the moment." # Test dividing by zero with pytest.raises(ValueError) as e: ret = resolver.solve(expression="50/0") assert str( e.value ) == "('The expression lead to a division by zero : ', 50.0, ' / ', 0.0)" # Test modulo by zero with pytest.raises(ValueError) as e: ret = resolver.solve(expression="50%0") assert str( e.value ) == "('The expression lead to a modulo zero : ', 50.0, ' % ', 0.0)" # Test dividing by zero for a var with pytest.raises(ValueError) as e: ret = resolver.solve(expression="X/0") assert str( e.value ) == "('The expression lead to a division by zero : ', 'X', ' / ', '0.0')" # Test modulo by zero for a var with pytest.raises(NotImplementedError) as e: ret = resolver.solve(expression="X%0") assert str( e.value ) == "This type of operation with vars is not accepted for the moment."
def test_calculator_with_one_var(): resolver = ExpressionResolver(verbose=False) # Test calc with var, only one var alone, should raise NothingToDoError with pytest.raises(NothingToDoError) as e: resolver.solve(expression="thisisavar") assert str( e.value ) == "There is no operators or sign in the expression. Nothing to do here." # Test calc with var, one var with simple addition ret = resolver.solve(expression="thisisavar + 5") assert ret == "5.0+THISISAVAR" # Test calc with var, one var with simple addition ret = resolver.solve(expression="5 + thisisavar + 5") assert ret == "10.0+THISISAVAR" # Test calc with var, one var with more complex addition ret = resolver.solve(expression="5 + thisisavar + 5 (-10 +(+5))") assert ret == "-20.0+THISISAVAR" # Test calc with var, one var with multiplication ret = resolver.solve(expression="5 * thisisavar") assert ret == "5.0*THISISAVAR" # Test calc with var, one var with multiplication ret = resolver.solve(expression="(5 * 2) * thisisavar") assert ret == "10.0*THISISAVAR" # Test calc with var, one var with multiplication ret = resolver.solve(expression="(5 * 2) * thisisavar * 2") assert ret == "20.0*THISISAVAR" # Test calc with var, one var with multiplication and additions ret = resolver.solve(expression="+ 2 - 5 + (5 * 2) * thisisavar * 2 - 500") assert ret == "-503.0+20.0*THISISAVAR" # Test calc with var, implicit mult ret = resolver.solve(expression="-5 - 2thisisavar2") assert ret == "-5.0-4.0*THISISAVAR" # Test calc with var, implicit mult ret = resolver.solve(expression="-5 - 2thisisavar(2(2+5))") assert ret == "-5.0-28.0*THISISAVAR" # Test calc with var, addition between var ret = resolver.solve(expression="x + x") assert ret == "2.0X" # Test calc with var ret = resolver.solve(expression="1 * x") assert ret == "X" # Test calc with var ret = resolver.solve(expression="5 * x") assert ret == "5.0*X" # Test calc with var ret = resolver.solve(expression="-1 * x") assert ret == "-X" # Test calc with var, addition between var ret = resolver.solve(expression="-5 - x + x * -1") assert ret == "-5.0-2.0X" # Test calc with var, sub between var ret = resolver.solve(expression="x - x") assert ret == "0.0" # Test calc with var, sub between var ret = resolver.solve(expression="54x - x(-2)") assert ret == "56.0X" # Test calc with var, multiplication between var ret = resolver.solve(expression="x * x") assert ret == "X^2.0" # Test calc with var, multiplication between var ret = resolver.solve(expression="x * 5x") assert ret == "5.0*X^2.0" # Test calc with var, multiplication between var ret = resolver.solve(expression="x * x * x + (5 * 2)") assert ret == "10.0+X^3.0" # Test calc with var, dividing var ret = resolver.solve(expression="x / 50 * x + (5 * 2)") assert ret == "10.0+0.02*X^2.0" # Test calc with var, dividing var by another var ret = resolver.solve(expression="x / 5 / x + (5 * 2)") assert ret == "10.2" # Test calc with var, dividing var by another var ret = resolver.solve(expression="2x / 5 / x + (5 * 2)") assert ret == "10.4" # Test calc with var, dividing var by another var ret = resolver.solve(expression="2x^5 / 5 / x + (5 * 2)") assert ret == "10.0+0.4*X^4.0" # Test calc with var, dividing var by another var ret = resolver.solve(expression="2x^5 / 5 / x *x + (5 * 2)") assert ret == "10.0+0.4*X^5.0" # Test calc with var, dividing var by another var ret = resolver.solve(expression="50x/x") assert ret == "50.0" # Test calc with var, power var ret = resolver.solve(expression="50x^2") assert ret == "50.0*X^2.0" # Test calc with var, power var ret = resolver.solve(expression="50x^(2+5)") assert ret == "50.0*X^7.0" # Test calc with var ret = resolver.solve(expression="-X ^ 3") assert ret == "-X^3.0" # Test calc with var ret = resolver.solve(expression="-X ^ 3 + X ^ 3") assert ret == "0.0" # Test calc with var ret = resolver.solve(expression="-X ^ 3 + x + X ^ 3") assert ret == "X" # Test calc with var ret = resolver.solve(expression="-X ^ 3 + + x ^ 2 +x + X ^ 3 - x") assert ret == "X^2.0" # Test calc with var ret = resolver.solve( expression="-X ^ 3 - 10X ^ 4+ x ^ 2 +x - x ^4 + X ^ 3 - x") assert ret == "-11.0X^4.0+X^2.0"