首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >为什么我的Python程序在UnicodeDecodeError中使用IntelliJ,但是从命令行中可以得到?

为什么我的Python程序在UnicodeDecodeError中使用IntelliJ,但是从命令行中可以得到?
EN

Stack Overflow用户
提问于 2012-09-13 15:01:00
回答 2查看 1.4K关注 0票数 1

我有一个简单的程序,加载一个.json文件,其中包含一个有趣的字符。程序(见下文)在终端中运行良好,但在IntelliJ中获得此错误:

UnicodeDecodeError:'ascii‘编解码器不能解码位置2的字节0xe2 :序数不在范围内(128个)

关键的守则是:

代码语言:javascript
运行
复制
with open(jsonFileName) as f:
    jsonData = json.load(f)

如果我把公开改为:

代码语言:javascript
运行
复制
with open(jsonFileName, encoding='utf-8') as f:

然后,它工作在IntelliJ和终端。我仍然是Python和IntelliJ插件的新手,我不明白它们为什么不同。我认为sys.path可能是不同的,但是输出使我认为这不是原因。谁能解释一下吗?谢谢!

版本:

  • 操作系统: Mac 10.7.4 (也在10.6.8上测试)
  • Python 3.2.3 (v3.2.3:3d0686d90f55,2012年4月10日,11:25:50) /Library/Frameworks/Python.framework/Versions/3.2/bin/python3.2
  • IntelliJ: 11.1.3极限

文件(2):

1. unicode-error-demo.py

代码语言:javascript
运行
复制
#!/usr/bin/python

import json
from pprint import pprint as pp
import sys

def main():
    if len(sys.argv) is not 2:
        print(sys.argv[0], "takes one arg: a .json file")
        return

    jsonFileName = sys.argv[1]
    print("sys.path:")
    pp(sys.path)
    print("processing", jsonFileName)

#    with open(jsonFileName) as f:           # OK in Terminal, but BUG in IntelliJ: UnicodeDecodeError: 'ascii' codec can't decode byte 0xe2 in position 2: ordinal not in range(128)
    with open(jsonFileName, encoding='utf-8') as f:     # OK in both
        jsonData = json.load(f)
        pp(jsonData)


if __name__ == "__main__":
    main()

2.编码-tem.json

代码语言:javascript
运行
复制
["™"]
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-09-13 15:03:54

JSON .load()函数需要Unicode数据,而不是原始字节。Python自动尝试使用默认编解码器(在您的例子中是ASCII)将字节字符串解码为Unicode字符串,但失败了。通过使用UTF-8编解码器打开文件,Python为您进行了显式转换。请参阅函数,它指出:

在文本模式中,如果未指定编码,则所使用的编码与平台有关。

将使用的编码确定如下:

  • 试试os.device_encoding(),看看是否有终端编码。
  • 使用函数,这取决于运行代码的环境。该函数的do_setlocale设置为False
  • 如果两个方法都返回了'ASCII',则使用None作为默认值。

所有这些都是用C语言完成的,但与python等价的是:

代码语言:javascript
运行
复制
if encoding is None:
    encoding = os.device_encoding()
if encoding is None:
    encoding = locale.getpreferredencoding(False)
if encoding is None:
    encoding = 'ASCII'

因此,当您在终端中运行程序时,os.deviceencoding()返回'UTF-8',但是在IntelliJ下运行时没有终端,如果没有设置任何区域设置,python将使用'ASCII'

Python Unicode HOWTO告诉您unicode字符串和字节字符串以及编码之间的区别。关于这一主题的另一篇重要文章是Joel的绝对最小Unicode知识项目

票数 4
EN

Stack Overflow用户

发布于 2012-09-13 15:18:24

Python2.x有字符串和unicode字符串。基本字符串用ASCII编码。ASCII只使用7位/char,允许编码128个字符,而现代UTF-8最多需要4个字节/字符。UTF-8与ASCII兼容(因此任何ASCII编码的字符串都是有效的UTF-8字符串),但不是相反。

显然,您的文件名包含非ASCII字符。默认情况下,python希望以简单的ascii编码字符串读取它,指出一个非ascii字符(它的第一个位不是0,因为它是0xe2),并说'ascii‘编解码器不能在位置2中解码字节0xe2 :序号不在范围内(128)。

与python无关,但仍然是我最喜欢的关于编码的教程:

http://hektor.umcs.lublin.pl/~mikosmul/computing/articles/linux-unicode.html

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/12409224

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档