# Replace part of expression

Hi, I've got an expression

X = (5/(e^(T*p) - 1) + 1/(e^(T*p) - e^(2*T)))*e^(T*p)/(80*e^(T*p) + e^(2*T*p))


(its result of D-transform - discrete laplace transform - don't know details, me bad in math) I need to replace e^(T*p) by z How can i do that ? Thanks!

edit retag close merge delete

Sort by » oldest newest most voted

Alternatively, you can write your expression out using Sympy, a symbolics package that's included with Sage. (Sympy Documentation)

sage: from sympy import *
sage: T = Symbol('T')
sage: p = Symbol('p')
sage: z = Symbol('z')
sage: X = (5/(exp(T*p) - 1) + 1/(exp(T*p) - exp(2*T)))*exp(T*p)/(80*exp(T*p) + exp(2*T*p))
sage: X.subs(exp(T*p),z)
z*(1/(z - exp(2*T)) - 5/(1 - z))/(80*z + z**2)


Note that Sympy correctly identifies that exp(2*T*p) == z^2. In some cases, Sympy can work better than the core of most of Sage's symbolics: Maxima. You should try both and see which one performs to your liking. You can easily switch from Sage's symbolic expressions to Sympy's by doing the following:

sage: import sympy
sage: var('T,p,z')
sage: X = (5/(e^(T*p) - 1) + 1/(e^(T*p) - e^(2*T)))*e^(T*p)/(80*e^(T*p) + e^(2*T*p))
sage: type(X)
<type 'sage.symbolic.expression.Expression'>
sage: Y = sympy.sympify(X)
sage: Y
(1/(-exp(2*T) + exp(T*p)) - 5/(1 - exp(T*p)))*exp(T*p)/(80*exp(T*p) + exp(2*T*p))
sage: type(Y)
<class 'sympy.core.mul.Mul'>


You can now treat Y similarly as above.

sage: Y.subs(exp(T*p),z)
z*(1/(z - exp(2*T)) - 5/(1 - z))/(80*z + z**2)


Note that we didn't have to convert T,p,z, nor exp to Sympy data types. Isn't that great?

EDIT: You can convert a Sympy expression back to a Sage symbolic expression by doing the following:

sage: Z = SR(Y.subs(exp(T*p),z))
sage: Z
(5/(z - 1) + 1/(z - e^(2*T)))*z/(z^2 + 80*z)
sage: Z(z=-1)
-1/79/(e^(2*T) + 1) - 5/158

more

Thanks for answer, Your solution is very "nice", but.. i have bad experience with importing packages, because they overrides some functions and classes (like libmathplot), e.g. before importing this package function "latex()" for "x=sin(y)+e^(3*y)" gives "e^{\left(3 \, y\right)} + \sin\left(y\right)", but after - e^{\\left(3 \\, y\\right)} + \\sin\\left(y\\right) - for me it's mean that I must edit it before put in openoffice document using latex extension, it's not a big trouble but I suspect that is only little thing that was replaced.

( 2011-05-28 00:18:56 -0500 )edit

Is there a way to convert Y, or Y.subs(exp(T*p), z), back to a Sage symbolic expression? Then you could call latex() on that.

( 2011-05-28 05:10:42 -0500 )edit

@avi9526 - To remedy that I suggest not writing statements like "from sympy import *" but instead using "import sympy" and calling functions and such using "sympy.somefunction()". That way you don't overwrite any of Sage's default namespace. @John Palmieri - Not sure. I know some Sympy developers wanted to make sympy play nice with Sage so they wrote that sympify() function. As for vice versa, I wonder if SR(Y) works...

( 2011-05-28 10:46:51 -0500 )edit

@John Palmieri Actually, SR(Y) does work! I made an edit above in my answer.

( 2011-05-28 10:53:41 -0500 )edit

Is this what you want?

sage: var('T p')
(T, p)
sage: X = (5/(e^(T*p) - 1) + 1/(e^(T*p) - e^(2*T)))*e^(T*p)/(80*e^(T*p) + e^(2*T*p))
sage: var('z')
z
sage: X.substitute(p=log(z)/T)
(5/(z - 1) + 1/(z - e^(2*T)))*z/(80*z + e^(2*log(z)))
sage: X.substitute(p=log(z)/T).simplify()
(5/(z - 1) + 1/(z - e^(2*T)))*z/(z^2 + 80*z)


or:

sage: X.substitute_expression(e^(p*T)==z)
(5/(z - 1) + 1/(z - e^(2*T)))*z/(80*z + e^(2*T*p))


(This second way doesn't seem to catch the last exponential piece.)

more

What's too bad about the X.substitute_expression() call is that the very last term should be z^2. Somehow, whatever Sage uses here (maxima?) can't recognize that.

( 2011-05-27 13:34:35 -0500 )edit