Question on “smart” replacing in mathematica

2019-02-05 05:14发布

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 /. a + b :> 1

Out = 2 a + b + c d + ec

I expect the answer to be a + cd + ec + 1. And before someone suggests, I don't want to do a :> 1 - b, because for aesthetic purposes, I'd like to have both a and b in my equation as long as the a+b = 1 simplification cannot be made.


In addition, how do I get it to replace all instances of 1-b, -b+1 or -1+b, b-1 with a or -a respectively and vice versa?

Here's an example for this part:

expr = b + c (1 - a) + (-1 + b)(a - 1) + (1 -a -b) d + 2 a

2条回答
一夜七次
2楼-- · 2019-02-05 05:41

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]
查看更多
一纸荒年 Trace。
3楼-- · 2019-02-05 05:45

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.

查看更多
登录 后发表回答