in reply to How to access each char in a string most quickly?

Here are a few alternatives assuming you cannot pre-split for your purpose.

My favorite hack is chop if I need speed and order does matter. It's about 4x faster than split and substantially faster than substr even if you have to reverse and copy for your needs. Better if you can avoid doing both, which you frequently can.

#! perl -sw use 5.010; use strict; use Benchmark qw[ cmpthese ]; our $LEN ||= 100; our $string = 'A' x $LEN; our @chars = split//, $string; cmpthese -3, { substr => q[ our $string; for ( 0 .. length $string ) { my $c = substr $string, $_, 1; } ], pre_split => q[ our @chars; for my $c ( @chars ) { ; } ], split => q[ our $string; my @chars = split //, $string; for my $c ( @chars ) { } ], unpack => q[ our $string; for ( unpack 'C*', $string ) { my $c = chr; } ], chop => q[ our $string; my $copy = $string; while( my $c = chop $copy ) { ; } ], rev_chop => q[ our $string; my $copy = reverse $string; while( my $c = chop $copy ) { ; } ], }; __END__ C:\test>byChar.pl Rate split unpack substr rev_chop chop p +re_split split 11018/s -- -74% -74% -81% -82% + -94% unpack 42513/s 286% -- -0% -26% -30% + -75% substr 42526/s 286% 0% -- -26% -30% + -75% rev_chop 57794/s 425% 36% 36% -- -5% + -66% chop 61056/s 454% 44% 44% 6% -- + -64% pre_split 171734/s 1459% 304% 304% 197% 181% + --

Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
"Science is about questioning the status quo. Questioning authority".
In the absence of evidence, opinion is indistinguishable from prejudice.
RIP PCW

Replies are listed 'Best First'.
Re^2: How to access each char in a string most quickly?
by ikegami (Patriarch) on Jul 03, 2009 at 02:27 UTC

      Neither stand up too well unless I've screwed something (which as we all know is entirely possible :):

      Update: Code corrected in light of ikegami's post below:

      C:\test>byChar.pl ... rgx_scalar => q[ our $string; while ( $string =~ /(.)/sg) { my $c = $1; } ], rgx_list => q[ our $string; for my $c ( $string =~ /(.)/sg) { ; } ], C:\test>byChar.pl Rate split rgx_list substr_refs rgx_scalar unpack subs +tr chop rev_chop pre_split split 9984/s -- -34% -74% -75% -76% -7 +7% -82% -83% -94% rgx_list 15104/s 51% -- -61% -62% -63% -6 +5% -73% -74% -91% substr_refs 38242/s 283% 153% -- -3% -7% -1 +2% -33% -34% -78% rgx_scalar 39574/s 296% 162% 3% -- -3% - +9% -30% -32% -77% unpack 40959/s 310% 171% 7% 3% -- - +6% -28% -29% -76% substr 43352/s 334% 187% 13% 10% 6% +-- -24% -25% -75% chop 56695/s 468% 275% 48% 43% 38% 3 +1% -- -2% -67% rev_chop 57962/s 481% 284% 52% 46% 42% 3 +4% 2% -- -67% pre_split 173576/s 1639% 1049% 354% 339% 324% 30 +0% 206% 199% --

      Examine what is said, not who speaks -- Silence betokens consent -- Love the truth but pardon error.
      "Science is about questioning the status quo. Questioning authority".
      In the absence of evidence, opinion is indistinguishable from prejudice.

        Neither stand up too well unless I've screwed something

        I didn't know how they'd compare.

        Very tired right now, but I think while ( my $c = $string =~ /(.)/sg) is wrong. $c will be 1 in the loop. Need to use $1.