A drawback of the Which command is that it evaluates x repeatedly until one of the conditions of Which is satisfied. This is time consuming when x is a complicated expression or/and when the set of conditions is large.
This is not true in Compile as x will always be a number or an array. Multiple uses of x won't slow anything down.
It isn't even true outside of Compile in most practical cases unless you defined x using := instead of =.
The command "Switch" only evaluates x once, but seems to be not compilable.
Simple forms of Switch are compilable. In your question, you are misusing Switch. It takes patterns, not true/false conditions. Please read the documentation.
When using it in Compile, only literal patterns seem to be accepted. An exception is the last pattern, which must be _ to handle the default case.
Example:
cf = Compile[{{x, _Integer}},
Switch[x,
1, 10,
2, 20,
_, 0
]
]
"
1 argument
2 Boolean registers
8 Integer registers
Underflow checking off
Overflow checking off
Integer overflow checking on
RuntimeAttributes -> {}
I0 = A1
I1 = 1
I4 = 20
I2 = 10
I3 = 2
I5 = 0
Result = I7
1 B0 = I0 == I1
2 if[ !B0] goto 5
3 I7 = I2
4 goto 11
5 B1 = I0 == I3
6 if[ !B1] goto 9
7 I6 = I4
8 goto 10
9 I6 = I5
10 I7 = I6
11 Return
"
If you try to use a more general pattern, such as _Integer or x_ /; x > 0, it will trigger a call to MainEvaluate (i.e. it won't be compiled) for that particular test.
Warning: When testing with literal patterns, it is important to be aware that 1. and 1 are considered to be different. We needed to explicitly specify that the input is an integer, otherwise it would be converted to a real (floating point) number, which never matches the integer 1. Thanks to @MichaelE2 for pointing this out!
In summary:
Inside Compile,
Applywill be compiled only if its first argument isTimesorPlus. – xzczd Sep 28 '16 at 12:02Switchin Mathematica, please check the document ofSwitchcarefully. – xzczd Sep 28 '16 at 12:10