2
$\begingroup$

All of the following

y[12]/.y[k_]-> If[EvenQ[k],a,b]
y[12]/.y[k_]-> If[OddQ[k],a,b]
y[11]/.y[k_]-> If[EvenQ[k],a,b]
y[11]/.y[k_]-> If[OddQ[k],a,b]
y[12]/.y->(If[OddQ[#],a,b]&)
y[12]/.f_[k_]-> If[EvenQ[k],a,b]

etc. give output b. Why?

$\endgroup$
2
  • 2
    $\begingroup$ It would be good to have an example to try, but my guess is that you need RuleDelayed instead of Rule. Try replacing -> with :>. $\endgroup$ – MassDefect Jun 2 '20 at 9:05
  • $\begingroup$ @MassDefect Absolutely! Thanks a lot. Could you put an answer? And I still would like to know why, if you know please $\endgroup$ – მამუკა ჯიბლაძე Jun 2 '20 at 9:07
4
$\begingroup$

In Mathematica, most functions with names ending in Q will always evaluate immediately to True or False, contrary to e.g. If or Positive:

EvenQ@5
(* False *)

EvenQ@k
(* False *)

If[True, a, b]
(* a *)

If[k, a, b]
(* If[k, a, b] *)

Positive@-3    
(* False *)

Positive@k
(* Positive[k] *)

Since Rule evaluates the right side immediately (contrary to RuleDelayed, where the right side is only evaluated once the values from the match are inserted), your code essentially does the following:

y[12] /. y[k_] -> If[EvenQ[k],a,b]
(* --> y[12] /. y[k_] -> If[False,a,b] *)
(* --> y[12] /. y[k_] -> b *)
(* --> b *)

Compare this with the RuleDelayed case:

y[12] /. y[k_] :> If[EvenQ[k],a,b]
(* --> If[EvenQ[12],a,b] *)
(* --> If[True,a,b] *)
(* --> a *)
$\endgroup$
5
  • $\begingroup$ Perfect answer, thanks! Could you please suggest where to read about this kind of special evaluation for functions depending on the syntactic structure of their heads? It was a complete surprise to me, and it is I believe important to know. Do you know where are such things documented? $\endgroup$ – მამუკა ჯიბლაძე Jun 2 '20 at 9:38
  • 1
    $\begingroup$ @მამუკაჯიბლაძე I don't think that "rule" *Q functions is explicitly documented somewhere. For a given function, you can see the behavior in the "Details & Options" section: E.g. for EvenQ is says: "EvenQ[expr] returns False unless expr is manifestly an even integer (i.e. has head Integer, and is even).", while for Positive it says: "Positive[x] gives False if x is manifestly a negative numerical quantity, a complex numerical quantity, or zero. Otherwise, it remains unevaluated." - Note how Positive is allowed to remain unevaluated, while EvenQ is not. $\endgroup$ – Lukas Lang Jun 2 '20 at 9:46
  • $\begingroup$ I see, thanks. Are you avare of any other similar "special treatment" cases? $\endgroup$ – მამუკა ჯიბლაძე Jun 2 '20 at 9:47
  • 1
    $\begingroup$ The only other case I can think of is for functions ending in Delayed, such as RuleDelayed, SetDelayed,... - contrary to their counterparts, the right side is only evaluated after the values from the match of the left side have been inserted. (As can be seen for RuleDelayed vs. Rule in the answer above) $\endgroup$ – Lukas Lang Jun 2 '20 at 9:58
  • 1
    $\begingroup$ @მამუკაჯიბლაძე You can also take a look at the output of Select[Length@# > 1 &]@ReverseSortBy[Length]@GroupBy[Last@StringSplit[#, a : (___?(Not@*LowerCaseQ) ~~ ___?LowerCaseQ) :> a] &]@Names["System*"]` - it gives a list of all symbols grouped by their suffix - some of the groups don't have a strong connection, but most do share many properties. You can take a look at the documentation of a few entries of each group to see what patterns you can spot $\endgroup$ – Lukas Lang Jun 2 '20 at 10:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.