I've been doing some benchmarking, mostly to learn how to use Benchmark, but also to test various intensive operations in some production code, and try to streamline them.
One of my bottlenecks involves code that copies a large array and then makes substitutions (via s///) to each element in the new copy. The code in question utilizes an unusal way of calling map{} to accomplish this (see the mapn in code). I came up with two alternative ways to do the same thing, and benchmarked them with surprising results.
#!/usr/bin/perl -w use strict; my @elem = (0..100_000); use Benchmark ':all'; cmpthese ( 100, { 'mapn' => sub { my @e = @elem; @e = map { $_ if (s/0/./g || 1) } @ +e }, 'for ' => sub { my @e = @elem; for (@e) { s/0/./g } }, 'mapc' => sub { my @e = map { $_ if (s/0/./g || 1) } @elem }, });
Results:
Rate mapn mapc for
mapn 0.703/s -- -41% -63%
mapc 1.19/s 70% -- -37%
for 1.89/s 170% 59% --
It is no surprise that both 'mapc' and 'for' tests are faster than 'mapn'. What surprised me was that 'for' was faster than 'mapc', mostly because I don't understand why. I ran the benchmark with arrays of various sizes, and with several different complexities of regex: the results are always extremely similar.
How does map{} differ from for(){}, and when is map faster (if ever)?
The Eightfold Path: 'use warnings;', 'use strict;', 'use diagnostics;', perltidy, CGI or CGI::Simple, try the CPAN first, big modules and small scripts, test first.
In reply to When should I use map, for? by radiantmatrix
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |