Optimization of sort()
Perlの最適化器はかなり頑張ってsort()の最適化を試みている。具体的には,配列をその場で直接ソートする場合,数値または整数でソートする場合,ソートブロックの$aと$bを単純に入れ替えた場合において,最適化された高速なバージョンが使われる。
以下はすべて5.10.0で確認した。
配列を直接ソートする場合
ソート後のリストを元の配列に代入するケース(たとえば"@array = sort @array")では,sort()に渡された配列を直接並び替えるため,メモリと速度の両方で勝る。
確認コード:
$ perl -MO=Concise,-exec -e '@a=sort@a' # ... 7 <@> sort lK/INPLACE # ...
ソートオペレータにおける「INPLACE」というフラグがこの最適化の表れである。
数値でソートする場合
ソートブロックでの数値による比較(たとえば"sort{ $a <=> $b } @array")は最適化され,Cで実装された高速なバージョンが使われる。
確認コード:
$ perl -MO=Concise,-exec -e '@a=sort{$a<=>$b}@a' #... 7 <@> sort lK/INPLACE,NUM # ...
ソートオペレータにおける「NUM」というフラグがこの最適化の表れである。
整数でソートする場合
integerプラグマによって整数による比較を行うことができるが,これは汎用数値比較よりもさらに高速なコードを生成する。
確認コード:
$ perl -MO=Concise,-exec -e 'use integer; @a=sort{$a<=>$b} @a' #... 7 <@> sort lK/INPLACE,INT,NUM # ...
ソートオペレータにおける「INT」というフラグがこの最適化の表れである。
逆順にソートする場合
ソートブロックの$aと$bを交換した逆順ソートにも対応している。
確認コード
$ perl -MO=Concise,-exec -e '@a =sort{$b cmp $a}@a' #... 7 <@> sort lK/DESC,INPLACE #...
ソートオペレータにおける「DESC」というフラグがこの最適化の表れである。
また,reverse sortにも対応しているが*1,DESCが初めから逆順にソートするのに対し,reverse sortは一旦ソートしてから逆順に並び返すためDESCの方が高速である。
*1:その場合はREVフラグが立つ。