6
$\begingroup$

Suppose I have a list of rules with a mix of values and equations on the RHS.

eqn={a->1,x->a+y,y->b,b->2}

How can I update the list such that RHS is evaluated using all the rules (assuming the list of rules is exhaustive and covers all variables)? This is what I want:

eqn={a->1,x->3,y->2,b->2}

I can do

Thread[Rule[eqn[[;; , 1]], eqn[[;; , 2]] //. eqn]]

But it looks too messy. Is there a simple function for this?

$\endgroup$
4
  • $\begingroup$ Since the new rule covers all variables,why not use the new rule directly? $\endgroup$
    – yode
    Commented Apr 17, 2017 at 22:30
  • $\begingroup$ @yode I don't have the new rule. I want to obtain the new rule by applying the old rule to itself. $\endgroup$
    – Stitch
    Commented Apr 17, 2017 at 22:31
  • $\begingroup$ MapAt[# //. eqn &, eqn, {All, 2}] comes to mind. $\endgroup$
    – C. E.
    Commented Apr 17, 2017 at 22:32
  • $\begingroup$ @C.E. Ahh, MapAt of course! Great! $\endgroup$
    – Stitch
    Commented Apr 17, 2017 at 22:37

3 Answers 3

6
$\begingroup$
MapAt[# //. eqn &, eqn, {All, 2}]

{a -> 1, x -> 3, y -> 2, b -> 2}

or

# -> (#2 //. eqn) & @@@ eqn

{a -> 1, x -> 3, y -> 2, b -> 2}

$\endgroup$
4
  • $\begingroup$ All other solutions are very nice too, but this is the fastest one, especially for messy lists. Also, it is the only one that doesn't eliminate the duplicates in the list and doesn't alter the order (not important, but good to have). $\endgroup$
    – Stitch
    Commented Apr 18, 2017 at 2:30
  • $\begingroup$ But you have not stated you hope to reserve those duplicates elements. :) $\endgroup$
    – yode
    Commented Apr 18, 2017 at 2:46
  • 1
    $\begingroup$ @yode The question is pretty clear on that actually, "how can I update the list such that RHS is evaluated using all the rules" is not the same as "How can I update the list such that RHS is evaluated using all the rules and deleete duplicates". Also OP's solution does not delete duplicates. $\endgroup$
    – C. E.
    Commented Apr 18, 2017 at 10:07
  • $\begingroup$ @yode The main reason this is the fastest solution -- the real list is much longer and is called many times, so the speed is important. The duplicates are nice, but not a deal breaker :) $\endgroup$
    – Stitch
    Commented Apr 18, 2017 at 16:48
7
$\begingroup$
Normal[<|eqn|>//.eqn]

{a->1,x->3,y->2,b->2}

$\endgroup$
7
$\begingroup$
Solve[Equal @@@ eqn][[1]]

{a -> 1, b -> 2, x -> 3, y -> 2}

Or

List @@ Rule @@@ Reduce[Equal @@@ eqn]

{y -> 2, x -> 3, b -> 2, a -> 1}

$\endgroup$
3
  • $\begingroup$ +1)..Good lesson for Reduce and Solve. :) $\endgroup$
    – yode
    Commented Apr 17, 2017 at 22:49
  • $\begingroup$ That's pretty nice! Didn't think about solving it in such an elegant way! $\endgroup$
    – Stitch
    Commented Apr 17, 2017 at 22:53
  • $\begingroup$ @yode, Stitch thank you both for the votes. $\endgroup$
    – kglr
    Commented Apr 17, 2017 at 22:58

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.