Python、Unicode、および Windows コンソール
質問
Windows コンソールで Unicode 文字列を出力しようとすると、 UnicodeEncodeError: 'charmap' codec can't encode character ....
エラー。これは、Windows コンソールが Unicode のみの文字を受け入れないためだと思います。これを回避する最善の方法は何ですか?Python に自動的に ?
この状況で失敗する代わりに?
編集: Python 2.5を使用しています。
注記: @LasseV.Karlsen のチェックマーク付きの回答は、ある意味時代遅れです(2008 年以降)。以下の解決策/回答/提案は慎重に使用してください。
@JFSebastianの答え 今日 (2016 年 1 月 6 日) の時点では、より関連性が高くなります。
解決
注記: この答えはちょっと時代遅れです(2008 年以降)。以下のソリューションは注意して使用してください。
問題と解決策を詳しく説明したページは次のとおりです (ページ内でテキストを検索してください) sys.stdout をインスタンスにラップする):
そのページからのコードの抜粋は次のとおりです。
$ python -c 'import sys, codecs, locale; print sys.stdout.encoding; \
sys.stdout = codecs.getwriter(locale.getpreferredencoding())(sys.stdout); \
line = u"\u0411\n"; print type(line), len(line); \
sys.stdout.write(line); print line'
UTF-8
<type 'unicode'> 2
Б
Б
$ python -c 'import sys, codecs, locale; print sys.stdout.encoding; \
sys.stdout = codecs.getwriter(locale.getpreferredencoding())(sys.stdout); \
line = u"\u0411\n"; print type(line), len(line); \
sys.stdout.write(line); print line' | cat
None
<type 'unicode'> 2
Б
Б
このページにはさらに詳しい情報が記載されているので、一読の価値があります。
他のヒント
アップデート: Python 3.6 実装する PEP 528:Windows コンソールのエンコードを UTF-8 に変更する: Windows のデフォルトのコンソールは、すべての Unicode 文字を受け入れるようになりました。 内部的には、次と同じ Unicode API を使用します。 の win-unicode-console
後述のパッケージ. print(unicode_string)
今すぐ働けばいいのです。
を取得します
UnicodeEncodeError: 'charmap' codec can't encode character...
エラー。
このエラーは、印刷しようとしている Unicode 文字が現在の (chcp
) コンソールの文字エンコーディング。コードページは多くの場合、次のような 8 ビット エンコーディングです。 cp437
約 1M の Unicode 文字のうち、約 0x100 文字のみを表すことができます。
>>> u"\N{EURO SIGN}".encode('cp437') Traceback (most recent call last): ... UnicodeEncodeError: 'charmap' codec can't encode character '\u20ac' in position 0: character maps to
これは、Windows コンソールが Unicode のみの文字を受け入れないためだと思います。これを回避する最善の方法は何ですか?
Windows コンソールは Unicode 文字を受け入れ、表示することもできます (BMP のみ) 対応するフォントが設定されている場合. WriteConsoleW()
API は、で提案されているように使用する必要があります。 @Daira Hopwoodの答え. 。これは透過的に呼び出すことができます。つまり、次のスクリプトを使用する場合、スクリプトを変更する必要はありませんし、変更すべきではありません。 win-unicode-console
パッケージ:
T:\> py -mpip install win-unicode-console
T:\> py -mrun your_script.py
見る Python 3.4、Unicode、さまざまな言語、Windows はどうなるのでしょうか?
Pythonを自動的に印刷する方法はありますか
?
この状況で失敗する代わりに?
すべてのエンコード不可能な文字を次の文字に置き換えるだけで十分な場合は、 ?
あなたの場合、設定できます PYTHONIOENCODING
環境変数:
T:\> set PYTHONIOENCODING=:replace
T:\> python3 -c "print(u'[\N{EURO SIGN}]')"
[?]
Python 3.6 以降では、次のように指定されたエンコードが使用されます。 PYTHONIOENCODING
envvar は、対話型コンソール バッファでは無視されます。 PYTHONLEGACYWINDOWSIOENCODING
envvar は空ではない文字列に設定されます。
不正な文字の信頼できる表現を取得することに興味がない場合は、次のようなものを使用できます (3.x を含む Python >= 2.6 で作業します)。
from __future__ import print_function
import sys
def safeprint(s):
try:
print(s)
except UnicodeEncodeError:
if sys.version_info >= (3,):
print(s.encode('utf8').decode(sys.stdout.encoding))
else:
print(s.encode('utf8'))
safeprint(u"\N{EM DASH}")
文字列内の不正な文字は、Windows コンソールで印刷可能な表現に変換されます。
以下のコードは、Windows でも Python 出力を UTF-8 としてコンソールに出力します。
コンソールは、Windows 7 では文字を適切に表示しますが、Windows XP では文字を適切に表示しません。ただし、少なくとも機能し、最も重要なことは、すべてのプラットフォームでスクリプトから一貫した出力が得られることです。出力をファイルにリダイレクトできるようになります。
以下のコードは、Windows 上の Python 2.6 でテストされました。
#!/usr/bin/python
# -*- coding: UTF-8 -*-
import codecs, sys
reload(sys)
sys.setdefaultencoding('utf-8')
print sys.getdefaultencoding()
if sys.platform == 'win32':
try:
import win32console
except:
print "Python Win32 Extensions module is required.\n You can download it from https://sourceforge.net/projects/pywin32/ (x86 and x64 builds are available)\n"
exit(-1)
# win32console implementation of SetConsoleCP does not return a value
# CP_UTF8 = 65001
win32console.SetConsoleCP(65001)
if (win32console.GetConsoleCP() != 65001):
raise Exception ("Cannot set console codepage to 65001 (UTF-8)")
win32console.SetConsoleOutputCP(65001)
if (win32console.GetConsoleOutputCP() != 65001):
raise Exception ("Cannot set console output codepage to 65001 (UTF-8)")
#import sys, codecs
sys.stdout = codecs.getwriter('utf8')(sys.stdout)
sys.stderr = codecs.getwriter('utf8')(sys.stderr)
print "This is an Е乂αmp١ȅ testing Unicode support using Arabic, Latin, Cyrillic, Greek, Hebrew and CJK code points.\n"
Giampaolo Rodolà の答えと似ていますが、さらに汚いものです。私は、エンコーディングの全体像と、それがどのように Windoze コンソールに適用されるかを理解するために、(近いうちに) 長い時間を費やすつもりです。
現時点では、プログラムがクラッシュしないことを意味する sthg が必要でしたが、それは理解していました...また、あまりにも多くのエキゾチックなモジュールをインポートする必要もありませんでした (特に私は Jython を使用しているため、半分の確率で Python モジュールが実際には利用できないことが判明します)。
def pr(s):
try:
print(s)
except UnicodeEncodeError:
for c in s:
try:
print( c, end='')
except UnicodeEncodeError:
print( '?', end='')
注意: "pr" は "print" よりも入力時間が短くなります (また、"safeprint" よりもかなり入力時間が短くなります)...!
Python スクリプトを実行する前に、コマンドラインに次のコードを入力するだけです。
chcp 65001 & set PYTHONIOENCODING=utf-8
Python 2 の場合は次を試してください。
print unicode(string, 'unicode-escape')
Python 3 の場合は次を試してください。
import os
string = "002 Could've Would've Should've"
os.system('echo ' + string)
または、win-unicode-console を試してください。
pip install win-unicode-console
py -mrun your_script.py
あなたの問題の原因は ない Win コンソールは Unicode を受け入れるつもりがありません (デフォルトで Win2k だと思うので、これを受け入れます)。これはデフォルトのシステムエンコーディングです。このコードを試して、何が得られるかを確認してください。
import sys
sys.getdefaultencoding()
ASCIIと書かれている場合、あなたの原因があります;-) sitecustomize.pyというファイルを作成し、pythonパスの下に置く必要があります(/usr/lib/python2.5/site-packagesの下に置いてください。 Win -C: python lib site -packagesなど)、次の内容があります。
import sys
sys.setdefaultencoding('utf-8')
また、ファイル内でエンコーディングを指定することもできます。
# -*- coding: UTF-8 -*-
import sys,time
編集:さらに詳しい情報が見つかります 優れた Dive into Python 本
TL;DR:
print(yourstring.encode('ascii','replace'));
私自身も Twitch チャット (IRC) ボットの開発中にこの問題に遭遇しました。(Python2.7最新)
返信するためにチャット メッセージを解析したいと思いました...
msg = s.recv(1024).decode("utf-8")
ただし、人間が読める形式でコンソールに安全に出力することもできます。
print(msg.encode('ascii','replace'));
これにより、ボットがスローする問題が修正されました UnicodeEncodeError: 'charmap'
エラーが発生し、Unicode 文字が次のように置き換えられました。 ?
.
Jによる回答に少し関連しています。F.セバスチャンですが、もっと直接的です。
コンソール/ターミナルに印刷するときにこの問題が発生する場合は、次の手順を実行します。
>set PYTHONIOENCODING=UTF-8
Python 3.6 Windows7:Python を起動するにはいくつかの方法があり、Python コンソール (Python のロゴが付いている) または Windows コンソール (cmd.exe と書かれている) を使用できます。
Windows コンソールで utf8 文字を印刷できませんでした。utf-8 文字を印刷すると、次のエラーがスローされます。
OSError: [winError 87] The paraneter is incorrect
Exception ignored in: (_io-TextIOwrapper name='(stdout)' mode='w' ' encoding='utf8')
OSError: [WinError 87] The parameter is incorrect
上記の答えを理解しようと試みましたが失敗した後、それは単なる設定の問題であることがわかりました。cmd コンソール ウィンドウの上部のタブを右クリックします。 font
lucidaコンソールを選択しました。
ジェームズ・スラックはこう尋ねた。
Python に自動的に「?」を出力させる方法はありますか?この状況で失敗する代わりに?
他のソリューションでは、Windows 環境を変更するか、Python 環境を置き換えることを推奨しています。 print()
関数。以下の答えは、Sulak の要求を満たすことに近づきます。
Windows 7 では、Python 3.5 は、 UnicodeEncodeError
次のように:
代わりに:print(text)
代わりの: print(str(text).encode('utf-8'))
Python は例外をスローする代わりに、印刷できない Unicode 文字を次のように表示するようになりました。 \xNN 16 進コード、例:
ハルマロ n\xe2\x80\x99\xc3\xa9tait プラス qu\xe2\x80\x99un ポイント ノワール
の代わりに
ハルマロ・ネタイト・プラス・クン・ポイント・ノワール
確かに、後者の方が望ましいです セテリス・パリバス, ただし、それ以外の点では、前者は診断メッセージとしては完全に正確です。Unicode をリテラルのバイト値として表示するため、エンコード/デコードの問題の診断にも役立ちます。
注記: の str()
それ以外の場合は上記の呼び出しが必要です encode()
これにより、Python は Unicode 文字を数値のタプルとして拒否します。