# How to obtain decimal value from .solve() ?

var('n')
f(x,n) = -x^-1 + (1.097e7)*((1/(n-1)^2) - (1/n^2))

for i in range (2,10):
L = f(x,i).solve(x)
print(L)

[x == (1/8227500)]

[x == (9/13712500)]

....


How can I have this display a float value for x, rather than a fraction?

edit retag close merge delete

Sort by » oldest newest most voted

Hello, @RyanG! There are a couple of ways to do what you want.

1. You could use the N() function with the right hand side (rhs) of your solutions:

var('n')
f(x,n) = -x^-1 + (1.097e7)*((1/(n-1)^2) - (1/n^2))

for i in range (2,10):
L = f(x,i).solve(x)
print(N(L[0].rhs()))


Let me explain the last line. Sage's solve() command returns a list of solutions. In this particular case, there only one solution, so we access that with L[0] (of course, if there was a second solution, it would be accessed with L[1], etc.). Now that solution has the form x == <some_number>, so we access that <some_number> with the rhs() command (of course, lhs() would access the variable x). Finally, we use the N() function in order to have a numerical approximation.

I must point out that this method will work only when there is a unique solution. If there were many solutions---like with a polynomial of degree two or three---, this code should be modified in order to deal with that. (If you need that more general code, feel free to ask, and I can send it to you.)

You can improve the output as follows:

var('n')
f(x,n) = -x^-1 + (1.097e7)*((1/(n-1)^2) - (1/n^2))

for i in range (2,10):
L = f(x,i).solve(x)
print(L[0].lhs(), '=', N(L[0].rhs()))

2. Sage has a find_root() function that works numerically, instead of symbolically as solve() does. You have to give it two arguments: the limits of the interval where you assume the root will be. You can "guesstimate" such interval by plotting your functions or simply use a crazy interval like $[0,100]$.

In this particular case, you roots seem to be in $[0,1]$, but I will use the interval $[0,10]$ just to be sure:

var('n')
f(x,n) = -x^-1 + (1.097e7)*((1/(n-1)^2) - (1/n^2))

for i in range (2,10):
L = f(x,i).find_root(0,10)
print('x =', L)


Of course, this method has the disadvantage that only finds one root per call. If there were more than one solution for any of your functions, only one would be found. But, again, in this particular case, your functions have only one root.

I hope this helps!

more

2

If solve returns [x==<value>] and you store this in L, you can extract <value> with L[0].rhs(), as explained by @dsejas, or x.subs(L). Even more, if solve returns more than one solution, you can get all of them with a loop of the form for sol in L:. Likewise, it is equivalent N(number) to n(number) or number.n(). Hence, an alternative, complete code that prints all the solutions in decimal form would be:

for i in range (2,10):
print("i=",i)
L = f(x,i).solve(x)
for sol in L:
print(x.subs(sol).n())

( 2020-03-07 19:53:58 +0200 )edit

Thank for your such a thorough explanation! As someone new to Sage it means a lot when others are willing to break down and explain trivial issues like this.

( 2020-03-08 17:37:12 +0200 )edit