List::UtilsBy::XSが書けました。
List::UtilsBy::XSを書いてます。 - Life is very short
の作業がとりあえずひと通り終わりました。
List::UtilsByのテストユーティリティがなぜか無限ループして
しまうことや、Lightweight Callback APIの制限があったり
しますが、List::UtilsByから持ってきたテストは概ね通っています。
ベンチマーク
Perl 5.14.1の結果は以下のようになりました。
Benchmarking List::Util and List::UtilsBy::XS Bench: sort_by Rate pp xs pp 7729/s -- -37% xs 12217/s 58% -- Bench: nsort_by Rate pp xs pp 9050/s -- -71% xs 31716/s 250% -- Bench: rev_sort_by Rate pp xs pp 7450/s -- -38% xs 11933/s 60% -- Bench: rev_nsort_by Rate pp xs pp 8426/s -- -74% xs 32582/s 287% -- Bench: max_by Rate pp xs pp 28768/s -- -26% xs 38711/s 35% -- Bench: min_by Rate pp xs pp 25373/s -- -33% xs 38059/s 50% -- Bench: uniq_by Rate pp xs pp 12426/s -- -56% xs 28109/s 126% -- Bench: partition_by Rate pp xs pp 11598/s -- -30% xs 16593/s 43% -- Bench: count_by Rate pp xs pp 17148/s -- -34% xs 26065/s 52% -- Bench: zip_by Rate pp xs pp 10288/s -- -45% xs 18797/s 83% -- Bench: zip_by Rate pp xs pp 160777/s -- -43% xs 283880/s 77% -- Bench: weighted_shuffle_by Rate pp xs pp 1532/s -- -76% xs 6279/s 310% -- Bench: bundle_by Rate pp xs pp 34796/s -- -26% xs 47287/s 36% --
だいたい早くなっています。Lightweight Callback APIを
使っていないものも思った以上に差が出ました。
制約
- コールバック関数内で $_を変更できないインタフェースがある
- コールバック関数内で @_でアクセスできないインタフェースがある
- extract_byで weak-referenceの情報を保持できない
初めの 2つは Lightweight Callback APIによるところだと思います。
(ドキュメントにはその APIが提供されないと書いている。
実装可能かもしれないけど、参考にできるものがない。)
最後の私の知識不足によるところだと思います。いくつか試して
みましたが、panicにしかなりませんでした。
Lightweight callback APIを使うに当たっての注意
Perl5.14.1で作業をしていたのですが、Perl5.8でも一応と思って
試したところ、リンクがちゃんとできないというエラーに会いました。
どこみても解決方法が書いていないということで、ソースコードに
grepをかけてみたら解決方法がわかりました。
Lightweight callback APIを使う場合は, コンパイル時のフラグに
"-DPERL_EXT"を付ける必要がありました。Changelogに書いてました。
List::Utilの為だけに追加されたもののようです。