# Solve cannot get algebraic answer without taking logarithm

I'm trying to solve the simple, one variable equation: 8^(3*x) = 16^(x+1).

I am new to Sage, so I assume that I am doing something wrong. I like the Jupyter notebook interface and am hoping to use SageMath as my "go to" tool.

Mathematica, wolframalpha, and Mathcad 6 (mupad symbolic engine) solve this as is (x=4/5).

Sage and Mathcad 7 (new symbolic engine) both seem to require what would be the first step if I were to do manual solve -- take log of both sides.

SageMath 9.2

Fails:

sage: x = var('x')
sage: assume(x,'real')
sage: solve( 8^(3*x)-16^(x+1)==0, x)
[8^x == 1/2*16^(1/3*x + 1/3)*(I*sqrt(3) - 1),
8^x == -1/2*16^(1/3*x + 1/3)*(I*sqrt(3) + 1),
8^x == 16^(1/3*x + 1/3)]


Works:

sage: x = var('x')
sage: assume(x,'real')
sage: solve( ln(8^(3*x))-ln(16^(x+1))==0, x)
[x == (4/5)]

edit retag close merge delete

Sort by » oldest newest most voted

Hello, @rogergun! This will be a little anticlimactic answer, but here we go. This problem that you point out is some of the annoyances of using SageMath. Like many other computer algebra systems (CAS) out there, Sage is not as "intelligent" (yes, I chose the word correctly) as a problem like this would require, so it needs the help of a human brain, which is intelligent enough. For example, in a Calculus book that my thesis advisor wrote, I could find a whole plethora of trigonometric limits that cannot be solved by SageMath, Mathematica and other CAS that I tried (unfortunately, I don't have access to Mathcad 6.) However, these limits can be solved by a human brain in no more than three steps applying some very simple trigonometric identities.

The problem you point out in your question is very annoying because it is so simple to solve for a human brain. Perhaps a future version of SageMath will be able to deal with such problems. However, always have in mind that even the most clever computer needs the human brain for one or another type of problem.

That being said, Sage is a very beautiful and useful system, and most of us, the users, tend to ignore such annoyances, given the insanely large list of benefits we find every day. I can suggest you a few ways to deal with this problem:

1. Write your own solver for this type of equations. (This could require some advance knowledge of SageMath.)
2. Open a ticket in Sage Trac requesting the addition of a feature like this.
3. Use SymPy Gamma, a beautiful and very very, useful alternative to Wolfram Alpha. It is open source and free/libre/gratis, as SageMath is. For example, here is your problem solved in SymPy Gamma. You will notice that it gives you the real root and some of the complex roots (the solution set is infinite, as pointed out in @Emmanuel Charpentier's comment below.)
4. Since SymPy is excellent in solving symbolic equations, you can use it from SageMath itself. (This is the advantage of Sage being written in Python!) There are many ways to do this; I will give you one of them here:

from sympy import solve as sysolve
x = var('x')
sols = sysolve(8^(3*x)-16^(x+1), x)


The beauty of this is that you can leave to SageMath do the appropriate conversions for SymPy. For example, notice that 8^(3*x)-16^(x+1) is not in Python notation (in particular, ** should be used for exponentiation); also, strictly speaking, x is a Sage variable, not a SymPy symbol (which otherwise should be declared with sympy.symbols()). However, Sage's preparser takes care of these details for you. Alternatively, you can also replace the third line with

 sols = sysolve(8**(3*x)-16**(x+1), x._sympy_())


where _sympy_() is a Sage method that converts an object to the adequate SymPy type.

This will return the same list of results as SymPy Gamma, including complex ones, which we don't want right now, so you can add this to your code:

for sol in sols:
if sol._sage_() in RR:
print(sol)


I have used the _sage_() method, which is an "opposite" of _sympy_(), in the sense that it converts a SymPy object to the adequate SageMath type. (Note that this method also converts types from other software to Sage's representation; for example from Mathematica, Maxima, Fricas, etc.) In Sage, RR is the notation for the real field.

Here is the complete code in SageCell.

Note: Sage has the syntax

sols = solve(8^(3*x)-16^(x+1), x, algorithm='sympy')


which should automatically call SymPy's solve method. Unfortunately, the result returned by SymPy is ConditionSet(x, Eq(2**(5*x) - 16, 0), Complexes), which Sage does not know how to convert back to its data types. (Perhaps this will also be fixed in a future version, since I seem to remember there are ongoing efforts to improve Sage-SymPy translations.)

I hope this helps!

more

Ahem...

sage: sympy.solve((8^(3*x)==16^(x+1))._sympy_(), x._sympy_())
[4/5,
4/5 - 4*I*pi/(5*log(2)),
4/5 - 2*I*pi/(5*log(2)),
4/5 + 2*I*pi/(5*log(2)),
4/5 + 4*I*pi/(5*log(2))]


Big fat hint... Check an intuition :

sage: k=var("k", domain="integer")
True


The solution is an infinite set.

By the way :

sage: mathematica.Reduce(8^(3*x)==16^(x+1),x)
Element[C, Integers] && x == (4 + ((2*I)*Pi*C)/Log)/5
sage: C=function("C")
sage: mathematica.Reduce(8^(3*x)==16^(x+1),x).sage().subs(C(1)==k)
2/5*I*pi*k/log(2) + 4/5


Thank you for the lucid detailed response to my issue. I feel fortunate to have stumbled into this problem rather than ignorantly going ahead "fat, dumb, and happy".

Hello, @Emmanuel Charpentier! You are right: the set of solutions is infinite. I don't know how this could escape me. Thank you for pointing this out! I have updated my answer to reference your comment.