トップ «前の日記(2006-10-06) 最新 次の日記(2006-11-06)» 編集

Public Diary


2006-10-27

[プログラミング] Encode.pm, Jcode.pm, Text::Iconv のベンチマーク比較

Encode.pm Jcode.pm のベンチマーク比較 ではEncode.pmとJcode.pmのベンチマークをとっていて便利。ただし、もう一つの変換系であるText::Iconvが含まれていなかったので、追試も兼ねてText::Iconvを含めたベンチマークをやってみる。スクリプトはこんな感じ:

use strict;
use warnings;
use Benchmark ':all';
use Jcode;
use Encode;
use Text::Iconv;
my $text = qq{ASCII, 漢字、カタカナ、ひらがなの混じったtext};

cmpthese(
  sort timethese(
    10000,
    {
      "Jcode::new" => sub {
        $text = Jcode->new($text)->utf8;
        $text = Jcode->new($text)->euc;
      },
      "Jcode::convert" => sub {
        Jcode::convert( \$text, 'utf8', 'euc' );
        Jcode::convert( \$text, 'euc', 'utf8' );
      },
      "Encode::from_to" => sub {
        Encode::from_to($text, "euc-jp", "utf-8");
        Encode::from_to($text, "utf-8", "euc-jp");
      },
      "Text::Iconv" => sub {
        my $cd1 = Text::Iconv->new("euc-jp", "utf8");
        $text = $cd1->convert($text);
        my $cd2 = Text::Iconv->new("utf8", "euc-jp");
        $text = $cd2->convert($text);
      },
    }
  )
);

結果は

Benchmark: timing 10000 iterations of Encode::from_to, Jcode::convert, Jcode::new, Text::Iconv...
Encode::from_to:  0 wallclock secs ( 0.57 usr +  0.00 sys =  0.57 CPU) @ 17543.86/s (n=10000)
Jcode::convert:  1 wallclock secs ( 0.44 usr +  0.00 sys =  0.44 CPU) @ 22727.27/s (n=10000)
Jcode::new:  3 wallclock secs ( 3.38 usr +  0.00 sys =  3.38 CPU) @ 2958.58/s (n=10000)
Text::Iconv:  1 wallclock secs ( 0.43 usr +  0.00 sys =  0.43 CPU) @ 23255.81/s (n=10000)
                   Rate   Jcode::new Encode::from_to Jcode::convert  Text::Iconv
Jcode::new       2959/s           --            -83%           -87%         -87%
Encode::from_to 17544/s         493%              --           -23%         -25%
Jcode::convert  22727/s         668%             30%             --          -2%
Text::Iconv     23256/s         686%             33%             2%           --

と、確かにEncode::from_toは速いんだけど一番速いのはText::Iconvだということがわかる。さらに、モジュールの読み込み時間の差も見てみると、

> time for i in `seq 1 100` ; do perl -MText::Iconv -e '' ; done
real 0m2.702s, user 0m2.440s, sys 0m0.260s

> time for i in `seq 1 100` ; do perl -MJcode -e '' ; done
real 0m3.664s, user 0m2.960s, sys 0m0.290s

> time for i in `seq 1 100` ; do perl -MEncode -e '' ; done
real 0m3.302s, user 0m2.980s, sys 0m0.320s

純粋なperlだけの起動時間は

> time for i in `seq 1 100` ; do perl -e '' ; done
real 0m0.310s, user 0m0.140s, sys 0m0.170s

ってことなので、Encodeが若干遅いことがわかる。

もちろんEncodeは標準で入っているというメリットがあるけど、5.8.0と5.8.1でのバージョン差異とかを考えると、使える人はText::Iconvを使ったほうが良いのかな、という気もします。ただText::Iconvには"fromcode"を指定する必要があるので、文字コードをどこで判別するのかという問題もあるわけですが…。

もっとも、こちらがやろうとしているのはperlのスクリプト作成じゃなくてC++なわけですが、まぁどの処理系を使おうかなぁ、という感じで。

(追記) C++でiconv

実際にiconvを利用するには、こういう使い方が想定されるだろう→「C++でiconv


1980|03|
1986|04|
1998|04|
2002|01|11|
2003|03|04|05|07|08|
2004|01|02|03|04|05|06|07|08|09|10|11|12|
2005|01|02|03|04|05|06|07|08|09|10|11|12|
2006|01|02|03|04|05|06|07|08|09|10|11|12|
2007|02|03|04|06|07|08|11|12|
2008|01|02|03|04|06|07|08|09|10|
2009|01|12|
2011|05|10|11|
2012|01|02|10|