Python 2.7中open()与gzip.open()文件模式为何存在差异?
嘿,这个问题我太有共鸣了!当初在Python2.7里折腾gzip模块时,也纳闷过为啥明明传的是rb/wb这种字符串模式,结果看到的却是一堆数字,和内置open()的输出完全不一样。其实这背后是gzip模块的底层实现逻辑在搞鬼,咱们来掰扯清楚:
底层调用的API不同导致模式展示差异
Python2.7的内置open()函数会直接保留你传入的字符串模式(比如'rb'),并在文件对象里展示出来。但gzip.open()和GzipFile不一样——它底层是调用os.open()来操作文件的,这个API接受的是整数型的文件状态标志(比如os.O_RDONLY对应只读,os.O_WRONLY | os.O_CREAT对应写入创建),所以gzip模块会把你传入的字符串模式转换成这些数字常量,最后展示出来的就是这些数字,而不是原来的字符串。传入已打开句柄时的模式解析逻辑
哪怕你把一个已经用内置open()打开的句柄传给GzipFile,它也不会去读取原句柄的字符串模式,而是直接从文件描述符里提取底层的数字状态标志,所以你看到的还是数字模式,而不是原句柄的rb/wb。不过放心,实际的读写行为是完全符合你预期的——比如你传的是只读模式打开的句柄,GzipFile也只会做只读操作。Python2.7的设计遗留问题
说白了这就是Python2.7时代gzip模块的一个小缺陷,到Python3里官方已经修复了这个问题,让gzip.open()的模式处理和内置open()保持一致,都会保留字符串模式的展示。Python2.7的gzip模块更偏向底层实现,没做上层的模式字符串兼容展示,才导致了这种“看起来不兼容”的错觉,但功能上完全没问题。
举个简单的验证例子,你可以在Python2.7里跑这两行代码:
import gzip print(gzip.open('test.gz', 'rb')) # 输出会带数字模式 print(open('test.txt', 'rb')) # 输出会显示 'rb' 模式
你会看到两者的模式展示差异,但实际读取文件的操作都是正常的。
内容的提问来源于stack exchange,提问作者filiprem

