所以,这是一个看似简单的问题,但我显然非常沉闷。我有一个小脚本从网页下载所有的.bz2文件,但由于某种原因,解压缩该文件给我带来了严重的问题。
我是一个Python新手,所以答案很明显,请帮助我。
在脚本的这一部分,我已经有了这个文件,我只是想把它读出来一个变量,然后解压缩?是对的吗?我已经尝试了各种方法来做到这一点,我通常在这个片段的最后一行得到“ValueError:找不到流的结尾”错误。我试图打开zipfile并以无数种方式将其写入字符串。这是最新的。
openZip = open(zipFile, "r")
s = ''
while True:
newLine = openZip.readline()
if(len(newLine)==0):
break
s+=newLine
print s
uncompressedData = bz2.decompress(s)
嗨Alex,我应该列出我尝试过的所有其他方法,因为我尝试过read()方式。
方法A:
print 'decompressing ' + filename
fileHandle = open(zipFile)
uncompressedData = ''
while True:
s = fileHandle.read(1024)
if not s:
break
print('RAW "%s"', s)
uncompressedData += bz2.decompress(s)
uncompressedData += bz2.flush()
newFile = open(steamTF2mapdir + filename.split(".bz2")[0],"w")
newFile.write(uncompressedData)
newFile.close()
我收到错误:
uncompressedData += bz2.decompress(s)
ValueError: couldn't find end of stream
方法B
zipFile = steamTF2mapdir + filename
print 'decompressing ' + filename
fileHandle = open(zipFile)
s = fileHandle.read()
uncompressedData = bz2.decompress(s)
同样的错误:
uncompressedData = bz2.decompress(s)
ValueError: couldn't find end of stream
非常感谢你的回复。我真的把头靠在墙上,因为无法解压缩简单的.bz2文件而感觉非常厚。
通过by,使用7zip手动解压缩,以确保文件没有任何问题,并且解压缩得很好。
答案 0 :(得分:14)
您正在打开并读取压缩文件,就像它是由行组成的文本文件一样。别!不是。
uncompressedData = bz2.BZ2File(zipFile).read()
似乎更接近你所追求的目标。
编辑:OP已经展示了一些他尝试过的东西(虽然我没有看到任何有关尝试过最佳方法的说明 - 我上面推荐的单线程!)但是他们似乎都有一个共同的错误,我重复上面的关键位:
打开...压缩文件好像 它是一个文本文件......它不是。
open(filename)
甚至更明确的open(filename, 'r')
打开,用于阅读文本文件 - 压缩文件是二进制文件,因此,为了正确阅读,您必须使用open(filename, 'rb')
打开它。 ((我的推荐bz2.BZ2File
知道它正在处理一个压缩文件,当然,所以没有必要再告诉它了))。
在Python 2.*
中,在Unix-y系统上(即除了Windows之外的所有系统),你可以匆匆使用open
(但在Python 3.*
你可以' t,因为文本是Unicode,而二进制是字节 - 不同的类型。)
在Windows中(以及之前在DOS中),因为Windows的文本文件由于历史原因而区分,所以始终是必不可少的(使用两个字节而不是一个到结束行,并且至少在某些情况下,取一个值为'\0x1A'
的字节表示文件的逻辑结尾),因此读写低级代码必须进行补偿。
所以我怀疑OP正在使用Windows并且正在为不小心使用'rb'
选项(“读取二进制”)来支付open
内置的价格。 (尽管bz2.BZ2File
仍然比较简单,无论你使用什么平台! - 。)。
答案 1 :(得分:9)
openZip = open(zipFile,“r”)
如果你在Windows上运行,你可能想在这里说 openZip = open(zipFile,“rb”),因为该文件很可能包含CR / LF组合,你不要不希望他们被翻译。
newLine = openZip.readline()
正如Alex指出的那样,这是非常错误的,因为“行”的概念对于压缩流来说是陌生的。
s = fileHandle.read(1024) [...] uncompressedData + = bz2.decompress(s)
出于同样的原因,这是错误的。 1024字节的块对解压缩程序来说不太可能有多大意义,因为它会想要使用它自己的块大小。
s = fileHandle.read() uncompressedData = bz2.decompress(s)
如果这不起作用,我会说这是我上面提到的新线翻译问题。
答案 2 :(得分:5)
这非常有帮助。 在Windows打开时,2300个文件中的44个文件丢失了文件。 添加b(inary)标志以打开问题。
for line in bz2.BZ2File(filename, 'rb', 10000000) :
运作良好。 (10M是缓冲大小,适用于所涉及的大文件)
谢谢!