Mathematica Asked on March 26, 2021
Related threads replacing-a-sum-of-expressions and Replace a sum of squared variables by a new squared variable
Given the identity $x+y+z=p$ I’d like to simplify the generic expression
$$kx+ly+mz$$
where $k$, $l$, $m$ are positive integer coefficients, but ultimately this shouldn’t matter.
The naive ansatz would be to use the rule
HoldPattern[Plus[x,y,z]]->p
This works fine when $k=1$, $l=1$, and $m=1$ but fails in all other cases. Now the accepted answer in the first linked post, states that you need to define all the rules manually. But this gives this massive object, which leads to $2^c$ possibilities, where $c$ is the number of coefficients.
HoldPattern[Plus[x, y, z]] -> p,
HoldPattern[Plus[Times[a_?IntegerQ, x], y, z]] :>
Plus[Times[a - 1, x], y, z, p],
HoldPattern[Plus[Times[a_?IntegerQ, y], x, z]] :>
Plus[Times[a - 1, y], x, z, p],
HoldPattern[Plus[Times[a_?IntegerQ, z], x, y]] :>
Plus[Times[a - 1, z], x, y, p],
HoldPattern[Plus[Times[a_?IntegerQ, x], Times[b_?IntegerQ, y], z]] :>
Plus[Times[a - Min[a, b], x], Times[b - Min[a, b], y], z, p],
HoldPattern[Plus[Times[a_?IntegerQ, x], Times[b_?IntegerQ, z], y]] :>
Plus[Times[a - Min[a, b], x], Times[b - Min[a, b], z], y, p],
HoldPattern[Plus[Times[a_?IntegerQ, y], Times[b_?IntegerQ, z], x]] :>
Plus[Times[a - Min[a, b], y], Times[b - Min[a, b], z], x, p],
HoldPattern[
Plus[Times[a_?IntegerQ, x], Times[b_?IntegerQ, y],
Times[c_?IntegerQ, z]]] :>
Plus[Times[a - Min[a, b, c], x], Times[b - Min[a, b, c], y],
Times[c - Min[a, b, c], z], Times[Min[a, b, c], p]]
}
It should be obvious, that
Example expected results:
What is the general way to apply the above identity to any expression?
Additional requirement (edited): $p$ should be able to be a more complicated expression, not necessarily atomic.
You can build another kind of rule
rule = a_. x + b_. y + c_. z :> (((a - min) x + (b - min) y +
(c - min) z + min p) /. {min -> Min[a, b, c]})
Then
(5x+2y+3z /.rule) == 2p+3x+z
(3x+2y /.rule) == 3x + 2y
Correct answer by evanb on March 26, 2021
Clear["Global`*"]
repl[expr_, vars : _List : {z, y, x}, p : _Symbol : p] :=
SortBy[expr /.
(Solve[Total[vars] == p, #][[1]] & /@ vars) // Simplify,
LeafCount][[1]]
5 x + 2 y + 3 z // repl
(* 2 p + 3 x + z *)
3 x + 2 y // repl
(* 3 x + 2 y *)
Answered by Bob Hanlon on March 26, 2021
You can use PolynomialReduce
for this:
reduce[e_, p_Symbol->r_, v_List] := Module[{min},
min = First @ Ordering[Coefficient[e,#]&/@v];
Replace[
PolynomialReduce[e, r, v[[min]]],
{{n_}, s_} :> s + n p
]
]
Then:
reduce[3x + 2y + 5z, p -> x + y + z, {x, y, z}]
reduce[3x + 2y, p -> x + y + z, {x, y, z}]
2 p + x + 3 z
3 x + 2 y
Answered by Carl Woll on March 26, 2021
ClearAll[f0]
f0 = Module[{$v}, $v /. Solve[Eliminate[{$v == #, #2}, #3], $v][[1]]] &;
Examples:
f0[a x + b y + c z, p == x + y + z, y] // Simplify
a x + b (p - x - z) + c z
f0[5 x + 2 y + 3 z, p == x + y + z, y]
2 p + 3 x + z
f0[5 x + 2 y + 3 z, p == x + y + z, z]
3 p + 2 x - y
f0[ 3 x + 2 y, p == x + y + z, z]
3 x + 2 y
f0[ x + 2 y + z, p == x + y + z, z]
p + y
f0[ x + 2 y + z, p == x + y + z, y]
2 p - x - z
Answered by kglr on March 26, 2021
Get help from others!
Recent Questions
Recent Answers
© 2024 TransWikia.com. All rights reserved. Sites we Love: PCI Database, UKBizDB, Menu Kuliner, Sharing RPP