in reply to Re^5: Write code diferently
in thread Write code diferently
As I said before, I made some benchmarks a few weeks ago to compare for and map, and for turned out to be faster. The conditions were different, so I did not insist so much when I saw your results. But, still I was a bit surprised. So thinking back to it, I made a quick test, then another, again another, etc., and the results are markedly different from yours.
The slight problem with your benchmark is that it appears not to do what you think and it reports phony results. Multiplying a value by 1 is not terribly useful, and part of your code is probably optimized away.
I tried to get some meaningful results with your code, and I had to increase the numbers to incredibly high values to get something seemingly significant. This is my code based on yours:
use strict; use warnings; use Benchmark; my @a = 1..1000000; timethese (10000000,{a=>q{map {1} @a},b=>q[map $_*=1, @a],c=>q[$_*=1 f +or @a] });
And the results:
a: 1 wallclock secs ( 0.75 usr + 0.00 sys = 0.75 CPU) @ 13 +368983.96/s (n=10000000) b: 0 wallclock secs ( 0.75 usr + 0.00 sys = 0.75 CPU) @ 13 +368983.96/s (n=10000000) c: 2 wallclock secs ( 1.70 usr + 0.00 sys = 1.70 CPU) @ 58 +78894.77/s (n=10000000)
Less than one second to process 10 million times an array with one million elements? My laptop isn't so powerful. More interestingly, the "a" code_ref, which does nothing is just exactly as fast as the "b" code_ref. Your benchmark, on which you base all your demonstration that I am wrong and that you are right, is just hot air and pure baloney. And it is plain wrong.
Now, let's do a real benchmark:
use strict; use warnings; use Benchmark; timethese ( 10000, { "idiomatic" => sub { my @array = 1..1000; $_ +=2 for @ +array; }, "map" => sub { my @array = 1..1000; m +ap { $_ +=2;} @array; } } );
Tested on HP_UX, v5.8.8 :
Benchmark: timing 10000 iterations of idiomatic, map... idiomatic: 3 wallclock secs ( 3.25 usr + 0.01 sys = 3.26 CPU) @ 306 +7.48/s (n=10000) map: 6 wallclock secs ( 5.91 usr + 0.01 sys = 5.92 CPU) @ 16 +89.19/s (n=10000)
Tested on VMS - v5.8.6 :
idiomatic: 2 wallclock secs ( 1.59 usr + 0.00 sys = 1.59 CPU) @ 62 +8.93/s (n=10000) map: 3 wallclock secs ( 2.88 usr + 0.00 sys = 2.88 CPU) @ 34 +7.22/s (n=10000)
Tested on AIX, v5.10.1 :
Benchmark: timing 10000 iterations of idiomatic, map... idiomatic: 2 wallclock secs ( 0.89 usr + 0.00 sys = 0.89 CPU) @ 112 +35.96/s (n=10000) map: 3 wallclock secs ( 1.70 usr + 0.00 sys = 1.70 CPU) @ 58 +82.35/s (n=10000)
Tested on Linux, v.5.14.2:
Benchmark: timing 10000 iterations of idiomatic, map... idiomatic: 1 wallclock secs ( 1.25 usr + 0.00 sys = 1.25 CPU) @ 80 +12.82/s (n=10000) map: 3 wallclock secs ( 2.31 usr + 0.00 sys = 2.31 CPU) @ 43 +30.88/s (n=10000)
Tested on Windows 7, v. 5.18.0 (Strawberry Perl):
Benchmark: timing 10000 iterations of idiomatic, map... idiomatic: 1 wallclock secs ( 1.01 usr + 0.00 sys = 1.01 CPU) @ 98 +61.93/s (n=10000) map: 2 wallclock secs ( 2.08 usr + 0.00 sys = 2.08 CPU) @ 48 +19.28/s (n=10000)
So, five different platforms, five different operating systems, five versions of Perl, including the most recent 5.18, and every time just about the same result: for is 1.81 to 2.01 faster than map.
Cargo cult? Just repeating like a parrot what others are saying? No, actual hard experimental results.
|
|---|
| Replies are listed 'Best First'. | |
|---|---|
|
Re^7: Write code diferently (A little knowledge is a dangerous thing.)
by BrowserUk (Patriarch) on Aug 26, 2013 at 21:21 UTC | |
by Laurent_R (Canon) on Aug 29, 2013 at 00:18 UTC | |
by BrowserUk (Patriarch) on Aug 29, 2013 at 00:49 UTC |