How do I tell mathematica to do this replacement smartly? (or how do I get smarter at telling mathematica to do what i want)
expr = b + c d + ec + 2 a;
expr
You can use a customised version of FullSimplify
by supplying your own transformations to FullSimplify
and let it figure out the details:
In[1]:= MySimplify[expr_,equivs_]:= FullSimplify[expr,
TransformationFunctions ->
Prepend[
Function[x,x-#]&/@Flatten@Map[{#,-#}&,equivs/.Equal->Subtract],
Automatic
]
]
In[2]:= MySimplify[2a+b+c*d+e*c, {a+b==1}]
Out[2]= a + c(d + e) + 1
equivs/.Equal->Subtract
turns given equations into expressions equal to zero (e.g. a+b==1
-> a+b-1
). Flatten@Map[{#,-#}&, ]
then constructs also negated versions and flattens them into a single list. Function[x,x-#]& /@
turns the zero expressions into functions, which subtract the zero expressions (the #
) from what is later given to them (x
) by FullSimplify
.
It may be necessary to specify your own ComplexityFunction
for FullSimplify
, too, if your idea of simple differs from FullSimplify
's default ComplexityFunction
(which is roughly equivalent to LeafCount
), e.g.:
MySimplify[expr_, equivs_] := FullSimplify[expr,
TransformationFunctions ->
Prepend[
Function[x,x-#]&/@Flatten@Map[{#,-#}&,equivs/.Equal->Subtract],
Automatic
],
ComplexityFunction -> (
1000 LeafCount[#] +
Composition[
Total,Flatten,Map[ArrayDepth[#]#&,#]&,CoefficientArrays
][#] &
)
]
In your example case, the default ComplexityFunction
works fine, though.
For the first case, you might consider:
expr = b + c d + ec + 2 a
PolynomialReduce[expr, {a + b - 1}, {b, a}][[2]]
For the second case, consider:
expr = b + c (1 - a) + (-1 + b) (a - 1) + (1 - a - b) d + 2 a;
PolynomialReduce[expr, {x + b - 1}][[2]]
(% /. x -> 1 - b) == expr // Simplify
and:
PolynomialReduce[expr, {a + b - 1}][[2]]
Simplify[% == expr /. a -> 1 - b]