• ベストアンサー

Python の utf16le デコードが化ける。

Python2.5で日本語を扱おうと試みています。 utf16le で書かれた "名" という文字を他の文字コードに変換しようとすると、なぜか"吊"に化けるという現象に悩んでいます。 他の文字ではこのような現象は見ていないのですが、何か使い方を間違っているのでしょうか? ちなみに、コンソールでは例えばna.txt の内容が "名"1文字として、 import codecs utf16_file = codecs.open('na.txt', 'r', 'utf_16_le') print utf16_file.readline() とすると"吊"が表示されてしまいます・・・。 どなたか原因に心当たりがあったら教えてください。m(_ _)m

質問者が選んだベストアンサー

  • ベストアンサー
  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.2

動作環境はどういったものでしょうか? それと対話環境で実行した場合、どこかで(スタートアップ時のコンフィグファイルとか) エンコーディングを指定していないと Python 2.5.1 (r251:54863, May 18 2007, 16:56:43) [GCC 3.4.4 (cygming special, gdc 0.12, using dmd 0.125)] on cygwin Type "help", "copyright", "credits" or "license" for more information. >>> import codecs >>> utf16_file = codecs.open('na.txt', 'r', 'utf_16_le') >>> print utf16_file.readline() Traceback (most recent call last): File "<stdin>", line 1, in <module> UnicodeEncodeError: 'ascii' codec can't encode character u'\u540d' in position 0 : ordinal not in range(128) >>> print utf16_file.readline(). File "<stdin>", line 1 print utf16_file.readline(). ^ SyntaxError: invalid syntax こんな風になると思うのですが。 で気がついたことが一つ。 >echo 吊名|nkf -S -w16|od -t x1 0000000 54 0a 54 0d 00 0d 00 0a 0000010 これはBigendianでの結果ですが、見ての通り'名'の 0x0aを 0x0dにすると'吊'です。 バイトストリームでCRLF変換ありで出力してたりしませんか?

finch_nk
質問者

お礼

どうもありがとうございます! ”バイトストリームをCRLF変換”がよく分からなかったのですが、色々調べてみた結果、どうやらそれが原因らしいことが分かりました。 (ほかにも文字コードの末尾?が0Dで終わる鰍やら倍が化けたのでそうだと思います。)  その線で解決できそうです!  どうもありがとうございました。

finch_nk
質問者

補足

早速ご回答ありがとうございます。 すみません。全くの初心者で ”バイトストリームでCRLF変換あり”という操作が分かりません・・・。 分かる限りでは、WindowsXP上でActivePython (2.5)を使っています。 設定の変更は、デフォルトのエンコードをsitecustomize.pyで cp932に指定したのみだと思います。 サンプルのファイルとして、"名"一文字にしましたが、実際には "紙に名前を書いた物が名刺である。"が "紙に吊前を書いた物が吊刺である。"となってしまいます・・・。

その他の回答 (3)

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.4

わたしがWindowsで使っているのはPythonの配布元で配布しているものです。 ActivePythonを入れて試すというのはちょっとできないのでその辺は申し訳ないのですが、 sitecustmize.pyを import sys sys.setdefaultencoding('cp932') にして以下のように動作しています >python Python 2.5 (r25:51908, Sep 19 2006, 09:52:17) [MSC v.1310 32 bit (Intel)] on win 32 Type "help", "copyright", "credits" or "license" for more information. >>> import sys >>> sys.getdefaultencoding() 'cp932' >>> def foo(): ... import codecs ... uf = codecs.open('na.txt', 'r', 'utf-16le') ... return uf.readlines() ... >>> foo() [u'\u540d\u523a\r\n'] >>> print foo()[0] 名刺 ファイルから読み込んできた状態でどうなっているか確認してもらえますか? とりあえず↑と同じ操作をやってもらえればOKです。

finch_nk
質問者

お礼

ご回答ありがとうございます。 結局ActivePythonのバージョンアップをしたら治ってしまいました・・・。 ただ、別環境では古いバージョンでも問題ないので、ActivePythonのせいではないはずです。やはり参考書などを見ながら何らかの設定をしてしまっていたのかも知れません。 どうもありがとうございました。

  • sakusaker7
  • ベストアンサー率62% (800/1280)
回答No.3

ActivePythonは使ったことがないので微妙に違うかもしれませんが、 print utf16_file.readline() を print utf16_file.readline().encode('sjis') としたらどうなりますか? あるいは、 import sys import os, msvcrt msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY) を実行してから試すと何か変化はありますか?

finch_nk
質問者

補足

ご回答ありがとうございます。 print utf16_file.readline().encode('sjis') としても、やはり"名"は化けました。 import sys import os, msvcrt msvcrt.setmode(sys.stdout.fileno(), os.O_BINARY) とすると、この段階で 16384 と表記され、その後は変化がありませんでした・・・。 ところで別のWindowsVistaのPCにActivePythonを入れて試したところ、 今度は問題なく動きました。 仕事で使っているのはXPの方なので、逆なら良かったのですが・・・。

  • notnot
  • ベストアンサー率47% (4900/10358)
回答No.1

Linux(Fedora8)のPython2.5.1だと問題なく処理できますね。 "名"が 540d で、"吊"が 540a なので、おそらく改行コードの問題でしょう。OSは何でしょうか?

finch_nk
質問者

お礼

どうもありがとうございました。 やはり改行コードの問題だったようです。 (ようです、というのは、ActivePythonのバージョンアップを兼ねて再インストールしたら治ってしまったのです・・・。多分、自分でなんか変な設定をして忘れていたのだと思います。お騒がせいたしました。) 改行コード?ということで、ほかの化ける文字を探していたら、似たような 文字コードのばかり(0Dで終わる)だったので、やはり改行コードを変換する過程でこれもいじっていたようです。  どうもありがとうございました。

finch_nk
質問者

補足

早速にご回答ありがとうございます。 WindowsXP上でActivePython (2.5)を使っています。 設定の変更は、デフォルトのエンコードをsitecustomize.pyで cp932に指定したのみだと思います。 文中でも化け、しかも他の文字には全く影響を与えません。 改行コードについて、いろいろ変えて試してみようと思います。 ありがとうございます。

関連するQ&A