8
$\begingroup$

Here is a function that take some time to evaluate:

n = 1000;
coeffs = RandomVariate[NormalDistribution[], n];
f[x_] := Sum[coeffs[[k]] Sin[k x]/k, {k, 1, n}];

If I just plot the function with 1000 sample points, it takes about 0.24 seconds on my machine:

Plot[Evaluate@f[x], {x, 0, 2 Pi}, PlotPoints -> n, MaxRecursion -> 0] // Timing

On the other hand, if I try to collect 1000 samples of the function into a table, it takes five times as long:

Table[Evaluate@f[x], {x, 0, 2 Pi, 2 Pi/n // N}] // Timing

(Without the // N Mathematica tries to evaluate things symbolically, which is even slower.)

What is going on, and how can I make the Table as fast as the Plot?

$\endgroup$
3
  • $\begingroup$ You can save about one-third of the time by removing the redundant Evaluate from your Table expression. Also, this result is entirely dependent on the MaxRecursion setting. If you remove this, or leave it in but increase its value, the plot takes longer than the table. $\endgroup$
    – Verbeia
    Commented Aug 28, 2013 at 3:53
  • 1
    $\begingroup$ I used MaxRecursion -> 0 expecting that the Plot would evaluate exactly 1000 regularly spaced sample points, just like the Table. (Well, the Table actually evaluates 1001 points, but close enough.) Is that not true? $\endgroup$
    – user484
    Commented Aug 28, 2013 at 4:01
  • $\begingroup$ I've read in few places that Table can be slow. Not sure why now. Yes, you are right, MaxRecursion -> 0 makes sure no more points are taken. $\endgroup$
    – Nasser
    Commented Aug 28, 2013 at 4:06

1 Answer 1

11
$\begingroup$

Try this:

n = 1000;
coeffs = RandomVariate[NormalDistribution[], n];
f[x_] := Sum[coeffs[[k]] Sin[k x]/k, {k, 1, n}];
Plot[Evaluate@f[x], {x, 0, 2. Pi}, PlotPoints -> n, MaxRecursion -> 0,
   Mesh -> All] // Timing

Mathematica graphics

With[{n = 1000},
 First@Timing[Table[Evaluate@f[x], {x, 0, 2. Pi, 2. Pi/n}]]
 ]

Mathematica graphics

2 times as fast as plot. I remembered my own question difference-of-speed-in-making-a-table on tables some time ago and this trick of making Table much faster. The point is : to keep it packed, need to have all limits be numerics ! When you had n in there, the upper limit was not. So the table was not packed. Now it is.

You could just also write

Table[Evaluate@f[x], {x, 0, 2. Pi, 2. Pi/1000}]

and get the speed advantage. The point again, all its limits needs to be numeric. See above question for more information and additional links on this subject.

Another example

2000 points. Table still about 2 times faster:

Mathematica graphics

$\endgroup$
5
  • 2
    $\begingroup$ Thanks! But for me it seems that the difference is not the presence of n or the addition of With. Doing First@Timing[Table[Evaluate@f[x], {x, 0, 2. Pi, 2. Pi/n}]] is fast while doing First@Timing[Table[Evaluate@f[x], {x, 0, 2 Pi, 2. Pi/n}]] as in my question is slow. (The difference is just one more decimal point.) $\endgroup$
    – user484
    Commented Aug 28, 2013 at 5:18
  • $\begingroup$ @Rahul I'm using v7 so I can't check; is the output of RandomVariate a packed array of Real numbers? $\endgroup$
    – Mr.Wizard
    Commented Aug 28, 2013 at 5:26
  • $\begingroup$ @Mr.Wizard: I'm just learning about packed arrays just now, so let me know if this is not how to check: PackedArrayQ is True and the Head of the first element is Real, so yes? $\endgroup$
    – user484
    Commented Aug 28, 2013 at 5:34
  • $\begingroup$ @RahulNarain That's correct. I added an answer that you'll have to test yourself but it might be informative. $\endgroup$
    – Mr.Wizard
    Commented Aug 28, 2013 at 5:39
  • $\begingroup$ Having read your linked question I see that With is necessary for multidimensional tables, which I will need in the future, so thanks for that too! Unfortunately I have already given you an upvote and a check mark, so all I can do now is leave an appreciative comment. :) $\endgroup$
    – user484
    Commented Aug 28, 2013 at 7:14

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.