18 December 2010

(Perl) Encode::Guessでファイルの文字エンコード形式を判定

Encode モジュールを使って、ファイルのエンコード形式を得る(判定する)方法

#!/usr/bin/perl use warnings; use strict; use utf8; use Encode::Guess qw/euc-jp shiftjis iso-2022-jp/; # 一つのエンコードに、二つ以上の選択肢を与えると、「選択できないエラー」が返る # エンコード形式は Encode::Config.pm 参照 #use Encode::Guess qw/euc-jp shiftjis cp932 iso-2022-jp 7bit-jis/; use Data::Dumper; # ファイル名のユーザ入力 print 'input filename : '; $_ = <STDIN>; chomp; unless(-f $_){ die "file not found\n"; } # ファイルから、改行を無視して、一気に読み込む open(FH, "<$_") or die("file open error\n"); my $strAllLines = undef; { local $/ = undef; # 改行を区切りとして使わない $strAllLines = <FH>; } close(FH); my $enc = Encode::Guess->guess($strAllLines); print Data::Dumper->Dumper(\$enc)."\n"; if(ref($enc) eq 'Encode::utf8'){ print("detect : utf8\n"); } elsif(ref($enc) eq 'Encode::Unicode'){ print("detect : ".$$enc{'Name'}."\n"); } elsif(ref($enc) eq 'Encode::XS'){ print("detect : ".$enc->mime_name()."\n"); } elsif(ref($enc) eq 'Encode::JP::JIS7'){ print("detect : ".$$enc{'Name'}."\n"); } else{ # 二つ以上のエンコードが推定される場合は、$encに文字列が返る print("unknown (".$enc.")\n"); }

実行結果の例

$ perl detect-encode.pl input filename : test.txt $VAR1 = 'Data::Dumper'; $VAR2 = \bless( do{\(my $o = '-1220372128')}, 'Encode::XS' ); detect : Shift_JIS $ perl detect-encode.pl input filename : test.txt $VAR1 = 'Data::Dumper'; $VAR2 = \bless( { 'Name' => 'utf8' }, 'Encode::utf8' ); detect : utf8 $ perl detect-encode.pl input filename : test.txt $VAR1 = 'Data::Dumper'; $VAR2 = \bless( { 'h2z' => 1, 'jis0212' => 0, 'Name' => 'iso-2022-jp' }, 'Encode::JP::JIS7' ); detect : iso-2022-jp

■ エラーになる例

use Encode::Guess qw/shiftjis cp932/; のように、同じエンコード種別を2つ指定した場合、「二つ以上にマッチした場合」となって、次のような結果になる。

$ perl detect-encode.pl input filename : test.txt $VAR1 = 'Data::Dumper'; $VAR2 = \'shiftjis or cp932'; unknown (shiftjis or cp932)