Why is B /. h -> #2 & not a pure function?

I am trying to plot the energy surface of the mean field Ising model, but I am running into a problem with setting the MeshFunctions for the plot.

F = 2 d M + h
u = -F σ
z = Exp[-β u]
Z = Sum[z, {σ, {-1, 1}}] // FullSimplify
M0 = Sum[z σ, {σ, {-1, 1}}]/Z // FullSimplify

b = Solve[M0 == M &&  F/M <= 6 d && d >= 1, {β}, Reals][[1]]

U = D[-Log[Z], β] // FullSimplify
c = D[Log[Z], {β, 2}] // FullSimplify
ρ = (-M + 1)/2 // FullSimplify
S = β U + Log[Z] // FullSimplify
T = 1/β // FullSimplify
A = -T Log[Z] // FullSimplify
Reduce[A == U - T S]

d = 2
pp[x_, y_, z_] :=
ParametricPlot3D[{x, y, z} /. b /. M -> If[h < 0, -1, 1] * m, {m, 0,
1}, {h, -2^2, 2^2}, AxesLabel -> {"x", "y", "z"},
MeshFunctions -> (T /. b /. h -> #2 &)]

pp[h, T, A]


The surface plots, but I get the error

MeshFunctions::invmeshf: "MeshFunctions-> T /. b /. h->#2& must be a pure function or a list of pure functions"


and no mesh.

However, as @MrWizard's answer shows, MeshFunctions -> (T /. h -> #2 &) works in simpler examples.

• Hm. It works in MMA 10.0.1. Which version of MMA are you using? – Oliver Jennrich Oct 29 '14 at 22:56
• @OliverJennrich I have 10.0 Linux Home Edition – Daniel Mahler Oct 29 '14 at 23:00
• @OliverJennrich You are right. I tried to simplify the example for posting, but I oversimplified it. I put in the example that actually fails now. – Daniel Mahler Oct 29 '14 at 23:17

Update. I was distracted by the incomplete code before but I believe I see the problem now.

Simply put h in MeshFunctions is not the h in your plotting function. Note the syntax highlighting that (when correct) exists to indicate this, present also in this simpler example:

ParametricPlot3D[{Cos[u], Sin[u] + Cos[v], Sin[v]}, {u, 0, 2 π}, {v, -π, π},
MeshFunctions -> (v + #2 &)]


The v in (v + #2 &) is colored dark blue indicating an undefined Symbol rather than teal indicating a localized (plot) Symbol (as in {v, -π, π}). This means that you cannot address the plot variable v by name from the MeshFunctions function. The message that it generates is bogus and misleading as it of course is a pure function; rather I think that it should issue a message that the function did not evaluate to a meaningful specification.

From the MeshFunctions documentation we learn that there is another way to access these values:

The arguments supplied to the ... MeshFunctions ... are as follows:

ParametricPlot               x, y, u or x, y, u, v

This means that you can use the appropriate Slot to access the plot variable that you want, e.g.:

ParametricPlot3D[{Cos[u], Sin[u] + Cos[v], Sin[v]}, {u, 0, 2 π}, {v, -π, π},
MeshFunctions -> (#4 + #2 &)]


There still remains the problem that your replacement:

T /. h -> #2


is not meaningful as there is no h in the definition of T and β is undefined.

I do not follow what you are attempting to do here but I see a couple of problems:

• Symbols M, b and B are never defined in your code.

• User Symbols generally should not start with capital letters to avoid conflicts with System Symbols, now or in the future.

If I define empty sets for the replacement Symbols the plot evaluates without error:

M = {};
b = {};
T = Cos[h];
B = T /. b;
pp[x_, y_, z_] :=
ParametricPlot3D[{x, y, z} /. b /. M -> If[h < 0, -1, 1]*m, {m, 0, 1}, {h, -2^2, 2^2},
AxesLabel -> {"x", "y", "z"}, MeshFunctions -> (B /. h -> #2 &)]

pp[h, m, 0]


Please provide a complete, working example that exhibits the error you describe.

• @MrWizard thanks for all your help. What I really want is to have T as the mesh. I originally had MeshFunctions -> (T /. b /. h -> #2 &) [I must have accidentally deleted the /.b at some point], but that gives the same type of error even though the RHS of b contains an h. – Daniel Mahler Oct 30 '14 at 4:55