I'm having trouble finding a way (if there is) to analyse an expression, identify a complex pattern in it and then replace it with another thing. I think it will be easier to explain my problem with the code.

I have these expressions for mx and my:

mz = MZ[x, y, t];
ang = ANG[t];
mzX = D[mz, x];
mzY = D[mz, y];
mod = Sqrt[(1 - mz^2)/(mzX^2 + mzY^2)];
mx = mod (Cos[ang] mzX + Sin[ang] mzY);
my = mod (-Sin[ang] mzX + Cos[ang] mzY);

I calculate the derivative of mx with respect to t, which yields a very complicated expression:

deriv = D[mx, t]

enter image description here

I want to identify the parts of it matching the definitions for mx and my. That may involve regrouping terms, distributing products, etc. And then, I want to replace those parts with "mx" and "my" to get an expression simpler to the eye. Note that FullSimplify does not achieve what I need.

Can anyone please help me?


3 Answers 3


Some thoughts. First, you may eliminate terms with sin and cos from mx and my:

scsols=Solve[({mx, my} /. {Sin[ANG[t]] -> s, Cos[ANG[t]] -> c}) == {Mx, 
My}, {c, s}] // FullSimplify//First

I introduced new Mx and My, they are labels for mx and my respectively. Next you make the same substitution of sin and cos into deriv and then substitute scsols into the result:

deriv /. {Sin[ANG[t]] -> s, Cos[ANG[t]] -> c}/.scsols//FullSimplify

This gives some expression including Mx (=mx) and My (=my) and other derivatives of MZ and ANG:

enter image description here

Maybe this is somehow "simpler to the eye.


You might want to look at Experimental`OptimizeExpression. So if you run ...

 Experimental`OptimizeExpression[D[mx, t], "OptimizationSymbol" -> z]

You get what essentially involves a program that finds subexpressions that occur frequently in your program and recursively builds a formula out of them. It will not solve all of the issues you raise, but I suspect it will help.


You could do it semi-manually:

MYoverMOD = (-Sin[ang] mzX + Cos[ang] mzY);
MXoverMOD = (Sin[ang] mzY + Cos[ang] mzX);
modSquared = (1 - mz^2)/(mzX^2 + mzY^2);
deriv = D[mx, t];
deriv /. {modSquared -> MOD^2, MXoverMOD -> MX/MOD};
Simplify[%, Assumptions -> MOD > 0];
% /. MYoverMOD -> MY/MOD

enter image description here

Here MOD $\equiv$ your mod, MX $\equiv$ your mx, and MY $\equiv$ your my.

If the subexpression appears several times, it can be a time-saver to use the simple substitution syntax.

For some reason I wasn't able to replace MOD directly (the square root symbol interferes), so I had to replace the expression under the square root with MOD^2, which gave Sqrt[MOD^2]. I then converted that to MOD using Simplify. I also had to do it in two steps to get the expression in a form that allowed MY to be substituted.


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.