18
$\begingroup$

Is there a function that replaces the first occurence of the expression instead of replacing all? For example, if I have HoldForm[x + 2 + 4 + x] /. x -> 4, is there a way to return 4 + 2 + 4 + x?

$\endgroup$
4
  • 2
    $\begingroup$ $f_x^x$ Which one is the first x ? $\endgroup$ Commented Sep 23, 2014 at 22:34
  • $\begingroup$ I'm not really sure, but I guess if you hit Ctrl+Shift+E, and the first occurence of x is what I meant $\endgroup$ Commented Sep 23, 2014 at 22:36
  • $\begingroup$ What I mean is that the order of the symbols in a general math expression doesn't mean anything "in general". Perhaps if you restrict the domain of the expressions ... $\endgroup$ Commented Sep 23, 2014 at 22:38
  • 1
    $\begingroup$ fun ClearAll[r]; r[4] := (r[4] = x; 4); HoldForm[x + 2 + 4 + x] /. x :> RuleCondition@r[4] and for less fun take a look at Position 4th arg + ReplacePart. $\endgroup$ Commented Sep 23, 2014 at 22:41

4 Answers 4

15
$\begingroup$

Another way:

hf = HoldForm[x + 2 + 4 + x] i = 0 hf /. (x :> 4 /; i++ == 0) 

4 + 2 + 4 + x

$\endgroup$
17
$\begingroup$

Well here's a way. Find the position of the first occurrence of x:

expr = HoldForm[x + 2 + 4 + x]; pos = Position[expr, x, -1, 1]; 

Then:

ReplacePart[expr, pos -> 4] 

4 + 2 + 4 + x

$\endgroup$
4
  • 6
    $\begingroup$ +1 With version 10, we can use FirstPosition, e.g. HoldForm[x + 2 + 4 + x] // ReplacePart[#, FirstPosition[#, x] -> 4] &. $\endgroup$ Commented Sep 24, 2014 at 5:22
  • $\begingroup$ @WReach I was just updating the answer with that optimization. I considered using FirstPosition but it doesn't seem to bring much benefit here (a bit of clarity I guess) so I used the general equivalent. $\endgroup$ Commented Sep 24, 2014 at 5:24
  • $\begingroup$ @Mr.Wizard, thanks for the update, certainly cleaner :) $\endgroup$ Commented Sep 24, 2014 at 5:38
  • $\begingroup$ @WReach, good point, I forgot about FirstPosition $\endgroup$ Commented Sep 24, 2014 at 5:39
3
$\begingroup$

Edit

For order preserving as Jens says, I changed Attributes

ClearAttributes[Plus, Orderless] HoldForm[7 + x + 2 + 4 + x + 5] /. f___ + x + l___ :> f + 4 + l 

7 + 4 + 2 + 4 + x + 5

And you can revert by SetAttributes[Plus, Orderless]


Origin

How about this

HoldForm[x + 2 + 4 + x] /. x + a___ -> 4 + a 

4 + 2 + 4 + x

$\endgroup$
4
  • $\begingroup$ It won't work with this example: HoldForm[7 + x + 2 + 4 + x] /. x + a___ -> 4 + a because the order isn't preserved. $\endgroup$ Commented Sep 24, 2014 at 2:25
  • $\begingroup$ @Jens : I got it, and I changed attributes. $\endgroup$ Commented Sep 24, 2014 at 4:37
  • $\begingroup$ Yes, that works. But now you'd have to do the same if it were Times instead of Plus... anyway, you put your finger exactly on the reason why the original didn't work, and changing the attributes is certainly a way to make it work. $\endgroup$ Commented Sep 24, 2014 at 5:21
  • $\begingroup$ Related: (30152) $\endgroup$ Commented Sep 24, 2014 at 5:26
3
$\begingroup$
expr = HoldForm[x + 2 + 4 + x]; expr[[##& @@ FirstPosition[expr, x]]] = 4; expr 

4 + 2 + 4 + x

$\endgroup$

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.