I wanted to draw some contours. I succeeded with this:
W1 = {p, -2, 2, 0.5};
W2 = {p, -10, 10, 1};
P = W1; ContourPlot[
Evaluate[Union[Table[y^2 == 2 p*x, Evaluate[P]],
Table[x^2 == 2 p*y, Evaluate[P]]]], {x, -5, 5}, {y, -5, 5}]
P = W2;
ContourPlot[Evaluate[
Union[Table[y^2 == 2 p*x, Evaluate[ P]],
Table[x^2 == 2 p*y, Evaluate[P]]]], {x, -5, 5}, {y, -5, 5}]
I don't like this solution. I used Evaluate[] a few times and I feel like it is unnecessary although without the function I get errors. Could anyone explain me that. I find the reference unhelpful (maybe that's my lack of language?) "causes expr to be evaluated even if it appears as the argument of a function whose attributes specify that it should be held unevaluated.".
Answer
ContourPlot
has the attribute HoldAll
. That means that it receives its arguments before they are evaluated. So, if you put as a first argument, something that evaluates to a list but it's not a list, it won't fit with the overloaded version of ContourPlot
that expects a list. The same happens with the second argument of Table
. Whether they end up not evaluating, using another overload, giving a warning, or simply taking more time than they should, that depends on the particular case at hand
Evaluate
is something that makes the containing function behave temporarily as non-holding. Try
SetAttributes[f, HoldAll];
f[x_]:=Hold[x];
f[2+2]
f[Evaluate[2+2]]
If you don't find this neat, what's usually done is use With
With[{P = P},
With[{lists = Union[Table[y^2 == 2 p*x, P], Table[x^2 == 2 p*y, P]]},
ContourPlot[lists, {x, -5, 5}, {y, -5, 5}]
]
]
Comments
Post a Comment