19
$\begingroup$

Solve returns a list of replacement rules

In: Solve[x + y == 3 && x - y == 6, {x, y}]
Out: {{x -> 9/2, y -> -(3/2)}}

I am only interested in the right hand side of these rules. To extract the right hand side I use substitution:

({x, y} /. sol)[[1]]

It gives

{9/2, -(3/2)}

This works, but it is not very elegant. You have to adapt the list of the variables, each time you solve for different variables. Is there a more general way to extract the right hand sides form a list of replacements?

Edit The number of variables and the number of solutions may both differ.

$\endgroup$
2
  • 5
    $\begingroup$ I think everyone uses practically the same. Personally I use the equivalent form x /. First@Solve[...] (if there's only one solution---there might be two). $\endgroup$
    – Szabolcs
    Commented Mar 19, 2012 at 9:17
  • 3
    $\begingroup$ I think using ReplaceAll is in fact the elegant solution. If you get used to working with rules this method offers a lot of flexibility (e.g. when dealing with the already mentioned multiple solutions). $\endgroup$
    – Yves Klett
    Commented Mar 19, 2012 at 9:30

8 Answers 8

15
$\begingroup$

I also think that what you are already using is the best way, but here is another one to toss into the mix:

Solve[x + y == 3 && x - y == 6, {x, y}][[1]] /. Rule -> (#2 &)
{9/2, -(3/2)}
$\endgroup$
3
  • $\begingroup$ This doesn't return the complete set of solutions, when there are more than only one. A simple improvement would be deleting [[1]] or setting [[All]]. My approach seems to be a bit unnecessarily sophisticated. $\endgroup$
    – Artes
    Commented Mar 19, 2012 at 19:55
  • $\begingroup$ @Artes that is a valuable note. I was attempting to duplicate the result that the OP wanted and he used [[1]] too. $\endgroup$
    – Mr.Wizard
    Commented Mar 19, 2012 at 21:11
  • $\begingroup$ This works very well when deleting [[1]]. When solving for many variables (10), I don't want to specify these variables twice. I think this is much more elegant then substitution. $\endgroup$
    – sjdh
    Commented Mar 21, 2012 at 14:13
13
$\begingroup$

Update: With Version 10 comes the convenient built-in function Values which can be used as an alternative to Part and ReplaceAll:

Values@@Solve[x + y == 3 && x - y == 6, {x, y}]
(* {9/2,-(3/2)} *)

or

Values@Solve[x + y == 3 && x - y == 6, {x, y}]
(* {{9/2,-(3/2)}}  *)

Another example - a ragged list of rules:

lst={{a->1,b->2},{c->3},{{d->4}},{e->5,{f->6,{g->7}}}};
Values[lst]
(* {{1,2},{3},{{4}},{5,{6,{7}}}} *)

Original post:

You can also use

  Solve[x + y == 3 && x - y == 6, {x, y}] /. (_ -> b_) -> b 

or

 Solve[x + y == 3 && x - y == 6, {x, y}] /. Rule[_, b_] -> b 

or

Solve[x + y == 3 && x - y == 6, {x, y}] // #[[All, All, 2]] &
$\endgroup$
1
  • $\begingroup$ Yet another variation: Cases[Solve[x + y == 3 && x - y == 6, {x, y}], r_Rule :> Last[r], Infinity] $\endgroup$ Commented Mar 19, 2012 at 13:31
12
$\begingroup$

What about

res=Solve[x + y == 3 && x - y == 6, {x, y}];
res[[1, All, 2]]

that gives

{9/2, -(3/2)}

as you wanted. This should work while using Solve for any finite number of linear simultaneous equations.

Actually Rules in Mathematica has similar structure as list of Length two. You can see that if you replace Rule in a expression with List.

a1 = {a -> 2, b -> 3};
a1 /. Rule -> List

resulting to

{{a, 2}, {b, 3}}

This is an example that shows List is an intrinsic structure in Mathematica language and part specification simply works on rules. As expected

a2 = {{a, 2}, {b, 3}};
{a1[[1, 2]], a2[[1, 2]]}

{2, 2}

gives the same result for the List as well as the list of Rule.

$\endgroup$
8
$\begingroup$

As others have already echoed, using ReplaceAll is in fact, the most commonly used way (and not considered inelegant). You can accommodate for varying variables by keeping a list of them separately. For example, you could do

vars = {x, y};
sol = Solve[x + y == 3 && x - y == 6, vars];
var /. sol // First

Out[1]= {9/2, -(3/2)}

However, if you feel using ReplaceAll like that is kludgy, then you can also use OptionValue which does exactly what you want:

OptionValue[sol, vars]

Out[2]= {9/2, -(3/2)}
$\endgroup$
6
$\begingroup$

You can always just use indexing to get the rhs, though I find it makes your code less readable. For your example:

sol[[All,All,2]] 

will give {9/2, -(3/2)}. Which should work in general as the second "column" of a rule list is the rhs.

$\endgroup$
4
$\begingroup$

It would be better to use the following :

{#[[1, 2]], #[[2, 2]]} & /@ Solve[x^2 + y == 4 && x - y == 2, {x, y}]
{{-3, -5}, {2, 0}}

Since in general given a system of equations may have more than only one solution.

Another more general approach is to use Table, because of different number of variables. For example when we have 3 variables in a system :

x^2 + y == 4 && x - y == 2 && x^3 + y - z^3 == 5

We could write :

Table[ #[[a, 2]], {a, 3}] & /@ 
       Solve[ x^2 + y == 4 && x - y == 2 && x^3 + y - z^3 == 5, {x, y, z}]

Edit

Instead of specifying how many variables there are we can just use this :

Column@Apply[List, #, {2}] & @ Solve[
             x^2 + y == 4 && x - y == 2 && x^3 + y - z^3 == 5, {x, y, z}]

enter image description here

or

Column@
   Apply[Composition[Part[#, 2] &, List], 
         Solve[x^2 + y == 4 && x - y == 2 && x^3 + y - z^3 == 5, {x, y, z}], {2}]

enter image description here

$\endgroup$
2
$\begingroup$

Since V10, we have Values:

Solve[x + y == 3 && x - y == 6, {x, y}]
Values@ %
(*
  {{x -> 9/2, y -> -(3/2)}}
  {{9/2, -(3/2)}}
*)

Or simply

Values@ Solve[x + y == 3 && x - y == 6, {x, y}]
$\endgroup$
0
$\begingroup$

In this solution,you can don't care about the structure of expressions

Clear[x, y]
Solve[x + y == 3 && x - y == 6, {x, y}] /. Rule -> Set

{{9/2, -(3/2)}}

$\endgroup$

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.