CGI-BBS > 基礎 > その他 > utf-8について文字化けをもとのコードに戻したい。


カレッヂ
カレッヂ


質問者 imoju  投稿日 2004/10/20(水) 01:35:38
例えば "掲示板" という文字、UTF-8でエンコードすると

"E6%8E%B2%E7%A4%BA%E6%9D%BF"
となると思います。

そして本来UTF-8のコードである "E6%8E%B2%E7%A4%BA%E6%9D%BF" が
$str =~ s/%([0-9A-Fa-f][0-9A-Fa-f])/pack("C",hex($1))/ge;
でデコードされると

"牙ず? "

となってしまいます。
この "牙ず? " を元のUTF-8のコード "E6%8E%B2%E7%A4%BA%E6%9D%BF" に戻すには
どのように処理したらいいのでしょうか?
どなたかご教授お願いいたします。

プロバイダ参照:
サーバのOS:(未選択)
パソコンのOS:(未選択)
エディタ:
FTPソフト:
サーバ移転:していない
改造:(未選択)
CGI習熟度:middle

回答者 しあわせのツボ  [削除]  投稿日 2004/10/20(水) 12:57:39
s/%([0-9A-Fa-f][0-9A-Fa-f])/pack("C",hex($1))/ge; は
URLエンコードをデコードしているだけで、結果がSJISなのかUTF-8なのかは関知しません。
それを判断し、必要なら変換をする部分が別にあるはずです。

おそらく、jcode.plを使っているのではありませんか?
jcode.plはUTF-8を扱えませんから、最低でもそれをJcode.pmか何かに置き換える必要があります。
Perl5.8以上なら標準でEncodeモジュールが使えます。
質問者 imoju  [削除]  投稿日 2004/10/20(水) 15:51:19
しあわせのツボさん回答ありがとうございます。
アクセスログの解析ソフトを改造しているのですが、
すでにあるログの中に"牙ず? "のようにデコードされてしまっている部分があります。

J-code.pmを組み込めば"牙ず? "を「掲示板」としてくれるのですが、
利用しているプロバイダには重くてエラーが出てしまうため
代わりにsimaguni.plを利用したいと思っています。

解析ソフトではログを
$str =~ s/([^\x21-\x24\x26-\x7E])/sprintf("%%%02X",unpack("C",$1))/ge;
でエンコードしたうえで様々な解析を行なっているようなのですが、
ログに記録された段階で"牙ず? "になってしまっていると
上記の処理では元のutf-8のコードに戻らないようで、
simaguni.plを導入しても変換の対象となりません。
そこでutf-8のコードに戻すエンコードの方法を質問した次第です。

アドバイスをお願いいたします。
回答者 しあわせのツボ  [削除]  投稿日 2004/10/20(水) 19:58:22
ログ自体の不良のように見えるので、残念ながらその復旧はまず不可能と思います。

ログが既にデコードされた状態で記録されているとのことですが、
そのデコードプログラムがデコードに失敗しているようです。
「掲示板」のようにごく短い文字列の場合、ヒントが限られているため、
それがSJISなのかEUCなのか何なのか、プログラムが見極めるのはかなり困難です。
その時点で判定を誤った場合、間違った前提のもとに変換されたデータは
化けると同時に高確率で壊れます。
壊れてしまったものを修復するのは、とても大変ですし、まず元通りにはなりません。
質問者 imoju  [削除]  投稿日 2004/10/20(水) 22:54:18
改造を試みているアクセスログ解析ソフトをオリジナルの状態で使用すると、
前述の方法でデコードされているためutf-8で検索された
$ENV{'HTTP_REFERER'};の一部が"牙ず? "のように文字化けしています。
アクセスログ解析ソフトの一部を改造して日本語変換にJcode.pmを導入すると、
utf-8で検索され、ログには"牙ず? "のように文字化した状態で記憶されているデータも正しく変換できるので
ログ自体の不良とは考えませんでした。
残念ながら、利用しているプロバイダでは
Jcode.pmを導入してもログのデータが大きくなるとエラーになってしまいます。
Jcode.pmのコードを読み解こうとも試みたのですがなにぶん知識が乏しく、
いかにしてutf-8から一度妙な漢字に化けてしまった文字が、
再度正しく日本語に変換できているのかわからず、
熟達者からのアドバイスをいただけるかとこちらの掲示板に質問させていただいています。
回答者 しあわせのツボ  [削除]  投稿日 2004/10/21(木) 15:18:46
さすがに私もJcode.pmの中身を読んだ訳ではないので、なんとも。
# 何をしてるか知らなくても使えるのが利点ですから。

ログ全体のエンコードは何ですか。EUCでしょうか。
UTF-8で「掲示板」と書き、それを無理やりEUCとして開いたところ、
「繻牙ず纛心」になりました。
可能性として、UTF-8文字列をEUCと誤判定>EUCからEUCとして扱われ変換されなかった>
変換されてないのでデータは壊れていない>Jcode.pmが再判定>今度は正しくUTF-8として処理、
という仮説は成り立ちます。
もしそうなら、改造すべきは「再判定時に正しくUTF-8と見做せるようにする」ことでしょうが、
そのあたりのロジックは素人に直せる難易度ではなさそうな…。

返信(回答)する

 


Web裏技