# solve gives 1, 2, or 3 answers depending if one value in my equation is a real, rational, or integer

Any idea why solve() is giving me different answers depending on what the value of 'g' is in my equations (see code below)? If g is a variable, an integer, or 1.0 then I get the two correct solutions (i.e. +&- a sqrt). If g is 1/4 or 1.1 I get an incomplete answer which I can get the two correct solutions by doing a solve on the solved solution. If g is a real whole number like 2,3 then I get 3 solutions: the two correct ones and a spurious one. I only discovered this behaviour when I tried eqs=[0==f(x).diff(x)(x=0),0==f(x)(x=0)]; solve(eqs,T_1,x_0) and sage hanged just calculating forever. Is there any general rules about how I should enter variables in equations for use with solve()? I want to know beforehand if something like /4 will cause problems in which case I could use v* instead and later, after using solve(), substitute with .subs(v=1/4)?

reset()
forget()
var('T_1,T_2,x_0,h,d,g')
def f(x):
return B_0 + B_1 * (x - x_0) + B_2 * sqrt((x - x_0) ^ 2 + g*d)

B_0 = T_2 * (x_0 - h)
B_1 = (T_1 + T_2) / 2
B_2 = (T_2 - T_1) / 2

def check_solutions(gval):
print("g = {0}".format(gval))
eqs=[0==f(x).diff(x)(x=0,g=gval),0==f(x)(x=0,g=gval)]
print("******eqs:")
print(eqs)
sol1 = solve(eqs,T_1)
print("******Solution for T_1:")
print(sol1)

print("******sub T_1 solution into 2nd equation:")
print(eqs.subs(sol1))
assume(h>0)
sol2 = solve(eqs.subs(sol1),x_0)
print("******Solutions for x_0")
print(sol2)
print("******Solve again for x_0")
print([solve(sol2[i],x_0) for i in range(len(sol2))])
print("*****************************************")

gvals=[g,1,1.0,2.0,2,1/4,1.1]
for i in range(len(gvals)):
check_solutions(gvals[i])


running this I get:

g = g
******eqs:
[0 == 1/2*(T_1 - T_2)*x_0/sqrt(d*g + x_0^2) + 1/2*T_1 + 1/2*T_2, 0 == -(h - x_0)*T_2 - 1/2*(T_1 + T_2)*x_0 - 1/2*(T_1 - T_2)*sqrt(d*g + x_0^2)]
******Solution for T_1:
[
T_1 == (x_0 - sqrt(d*g + x_0^2))*T_2/(x_0 + sqrt(d*g + x_0^2))
]
******sub T_1 solution into 2nd equation:
0 == -(h - x_0)*T_2 - 1/2*((x_0 - sqrt(d*g + x_0^2))*T_2/(x_0 + sqrt(d*g + x_0^2)) + T_2)*x_0 - 1/2*((x_0 - sqrt(d*g + x_0^2))*T_2/(x_0 + sqrt(d*g + x_0^2)) - T_2)*sqrt(d*g + x_0^2)
******Solutions for x_0
[
x_0 == -sqrt(-d*g + h^2),
x_0 == sqrt(-d*g + h^2)
]
******Solve again for x_0
[[x_0 == -sqrt(-d*g + h^2)], [x_0 == sqrt(-d*g + h^2)]]
*****************************************
g = 1
******eqs:
[0 == 1/2*(T_1 - T_2)*x_0/sqrt(x_0^2 + d) + 1/2*T_1 + 1/2*T_2, 0 == -(h - x_0)*T_2 - 1/2*(T_1 + T_2)*x_0 - 1/2*(T_1 - T_2)*sqrt(x_0^2 + d)]
******Solution for T_1:
[
T_1 == (x_0 - sqrt(x_0 ...
edit retag close merge delete

This is a really good question, and likely has something to do with how we/Maxima convert certain constants - at times it replaces certain numbers by 'equivalent' fractions, I think (? or vice versa) which has caused related issues. If you can come up with a smaller example, or find the most distilled pieces of your example, that will make it that much easier to help you for us.

@kcrisman here's a smaller example that starts misbehaving for reals: reset() forget() var('h,x,g') assume (h>0) print(solve(sqrt(x+g)==h,x)) print(solve(sqrt(x+1)==h,x)) print(solve(sqrt(x+2.0)==h,x)) print(solve(sqrt(x+1/4)==h,x)) print(solve(sqrt(x+2.5)==h,x)) myrr.<rr> = PolynomialRing(RR) print(solve(sqrt(x+rr)==h,x)) which gives: x == h^2 - g x == h^2 - 1 x == h^2 - 2 1/2*sqrt(4*x + 1) == h 1/2*sqrt(2*x + 5)*sqrt(2) == h and a traceback error on the last example with rr (not enough space in comment to show). Other polynomial rings (CC,ZZ,QQ) gave the correct answer.

Also, in my original question if I replace sol2 = solve(eqs.subs(sol1),x_0) with sol2 = solve(eqs.subs(sol1).expand(),x_0), i.e. expand before solving, I get x0 = some function of x0 which is wrong.

In addition to my first comment to @kcrisman for the case where g = 1/4 if I run solve() on the incomplete answer that solve() originally gave me then I get the correct answer: solve(1/2*sqrt(4*x + 1) == h,x) gives: x == h^2 - 1/4 Why doesn't solve() give me that answer in the first place?

Sort by » oldest newest most voted

Thanks for the shorter versions! I'll repeat them here.

var('h,x,g')
assume (h>0)
print(solve(sqrt(x+g)==h,x))
print(solve(sqrt(x+1)==h,x))
print(solve(sqrt(x+2.0)==h,x))
print(solve(sqrt(x+1/4)==h,x))
print(solve(sqrt(x+2.5)==h,x))


This is all, as I suspected, already present inside Maxima.

(%i2) assume(h>0);
(%o2)                               [h > 0]
(%i3) solve(sqrt(x+g)=h,x);
2
(%o3)                            [x = h  - g]
(%i4) solve(sqrt(x+1)=h,x);
2
(%o4)                            [x = h  - 1]
(%i5) solve(sqrt(x+2.0)=h,x);

rat: replaced 2.0 by 2/1 = 2.0
2
(%o5)                            [x = h  - 2]
(%i6) solve(sqrt(x+1/4)=h,x);
sqrt(4 x + 1)
(%o6)                         [------------- = h]
2
(%i7) solve(sqrt(x+2.5)=h,x);

rat: replaced 2.5 by 5/2 = 2.5
sqrt(2 x + 5)
(%o7)                         [------------- = h]
sqrt(2)
(%i9) solve(sqrt(4*x+1)/2=h,x);
2
4 h  - 1
(%o9)                           [x = --------]
4


Hmm. Clearly there is something internal that is different once the denominator is not one, but it is puzzling. I've asked the Maxima list if they have any explanation.

This doesn't answer the RR question, or address it.

more