I measured this
sub abused_map {
my @sqrt_results;
map { push @sqrt_results, sqrt $_ } @results;
return;
}
and it turned out it's as fast as (well actually a hair faster than) the simple
for, which means that map is faster than for for iterating through elements,
but slower than for at building results.
I suspect that this is due to the aggregate nature: all the elements
are copied to the stack, and then all the elements are copied to the
array.
It's bullshit that the array size is preknown, etc.
As far as the opcodes go, map and for are pretty much the same, they
are looping constructs. Map is implemented kind of like 'while', the
mapping opcode is invoked repeatedly, once per element..
Reading through pp_mapwhile (in pp_ctl.c) it's appears that map actually needs
to copy parts of the stack often, due to the way that the input and the output
are both present on it.
There are comments int he source code, on how one could implement it better.
This also explains why abused_map is .
On Mon, Jun 30, 2008 at 09:10:46 +0300, Yossi Itzkovich wrote:
> Hi,
>
> In "Perl Best Practices" by Damian Conway I saw a guideline called "Use map
> instead of for when generating new lists from old". He explains there very
> well ,why map() will run faster then simple for when you generate new list
> from old one, for example: map is written in c, knows the final array size
> from the beginning (assuming you return a scalar from the mapping code) and
> more.
>
> I tried the code below on Solaris with (perl 5.6.1 and 5.8 ) and Linux (perl
> 5.10) and got results that map is slower 10-40% than simple for.
> Can someone explains it ?
>
> The code:
> #! /bin/env perl
>
> use strict;
> use warnings;
> use Benchmark qw(cmpthese);
>
> my @results=( 1 .. 100000);
>
> sub simpleFor
> {
> my @sqrt_results;
> for my $result (@results)
> {
> push @sqrt_results, sqrt($result);
> }
> }
>
>
> sub optimizedFor
> {
> my @sqrt_results;
>
> # Preallocate as many elements as @results already has...
> $#sqrt_results = $#results;
>
> for my $next_sqrt_result (0..$#results) {
>
> $sqrt_results[$next_sqrt_result] = sqrt $results[$next_sqrt_result];
> }
> }
>
> sub usingMap
> {
> my @sqrt_results = map { sqrt $_ } @results;
> }
>
>
> cmpthese (100,
> {"simple for" => 'simpleFor();',
> "optimized for" => 'optimizedFor()',
> "with map" => 'usingMap()',
> }
> );
>
>
>
>
> _______________________________________________
> Perl mailing list
> [email protected]
> http://perl.org.il/mailman/listinfo/perl
--
Yuval Kogman <[EMAIL PROTECTED]>
http://nothingmuch.woobling.org 0xEBD27418
pgpXrz2G0EGFU.pgp
Description: PGP signature
_______________________________________________ Perl mailing list [email protected] http://perl.org.il/mailman/listinfo/perl
