1. ホーム
  2. json

[解決済み] UnicodeDecodeError: 'utf8' コーデックは位置3131のバイト0x80をデコードできません: 不正なスタートバイトです

2022-02-24 23:24:12

質問

Python 2.7.12を使って、jsonファイルからtwitterのデータを読み込もうとしています。

使用したコードはこのようなものです。

    import json
    import sys
    reload(sys)
    sys.setdefaultencoding('utf-8')

    def get_tweets_from_file(file_name):
        tweets = []
        with open(file_name, 'rw') as twitter_file:
            for line in twitter_file:
                if line != '\r\n':
                    line = line.encode('ascii', 'ignore')
                    tweet = json.loads(line)
                    if u'info' not in tweet.keys():
                        tweets.append(tweet)
    return tweets

得られた結果

    Traceback (most recent call last):
      File "twitter_project.py", line 100, in <module>
        main()                  
      File "twitter_project.py", line 95, in main
        tweets = get_tweets_from_dir(src_dir, dest_dir)
      File "twitter_project.py", line 59, in get_tweets_from_dir
        new_tweets = get_tweets_from_file(file_name)
      File "twitter_project.py", line 71, in get_tweets_from_file
        line = line.encode('ascii', 'ignore')
    UnicodeDecodeError: 'utf8' codec can't decode byte 0x80 in position 3131: invalid start byte

同じような問題の回答をすべて見て、このコードにたどり着き、前回はうまくいったのですが、今回はどうでしょうか?なぜ今それが動作しないのか、手がかりがありません...私はどんなヘルプを感謝します!

どのように解決するのですか?

を持っていることは、何の役にも立ちません。 sys.setdefaultencoding('utf-8') これは厄介なハックで、あなたのコードから削除する必要があります。 参照 https://stackoverflow.com/a/34378962/1554386 詳しくはこちら

エラーが発生するのは line は文字列であり、あなたは encode() . encode() は文字列がUnicodeの場合のみ意味を持つので、Pythonはデフォルトのエンコーディングを使って最初にUnicodeに変換しようとします。 UTF-8 しかし、本来は ASCII . どちらかです。 0x80 は有効なASCIIまたはUTF-8ではないので失敗します。

0x80 は一部の文字セットで有効です。で windows-1252 / cp1252 それは .

ここでのコツは、データのエンコーディングをコード全体で理解することです。今のところ、あなたは多くのことを偶然に任せています。Unicode String型は便利なPythonの機能で、エンコードされたStringをデコードし、データの書き込みや転送が必要になるまでエンコードのことを忘れておくことができます。

を使用します。 io モジュールを使えば、テキストモードでファイルを開き、その都度デコードすることができます。 .decode() ! 受信データのエンコーディングを統一する必要があります。外部で再エンコードするか、スクリプトの中でエンコードを変更することができます。ここでは、エンコーディングを windows-1252 .

with io.open(file_name, 'r', encoding='windows-1252') as twitter_file:
    for line in twitter_file:
        # line is now a <type 'unicode'>
        tweet = json.loads(line)

io モジュールは、ユニバーサル改行も提供します。これは \r\n は改行として検出されるため、改行の有無を確認する必要はありません。