gzip.open().read() 的大小参数
The size parameter for gzip.open().read()
在 Python 中使用 gzip
库时,我经常会遇到以如下形式使用 .read()
函数的代码:
with gzip.open(filename) as bytestream:
bytestream.read(16)
buf = bytestream.read(
IMAGE_SIZE * IMAGE_SIZE * num_images * NUM_CHANNELS
)
data = np.frombuffer(buf, dtype=np.uint8).astype(np.float32)
虽然我熟悉上下文管理器模式,但我很难真正理解 with
上下文管理器中的第一行代码到底在做什么。
这是 read()
函数的文档:
Read at most n characters from stream.
Read from underlying buffer until we have n characters or we hit EOF.
If n is negative or omitted, read until EOF.
如果是这种情况,第一行 bytestream.read(16)
的功能作用必须是读取并因此跳过前 16 个字符,大概是因为它们充当 meta-data 或 header.但是,当我有一些图像时,我怎么知道使用 16
作为 read
调用的参数,而不是 32、8 或 64?
我记得有很多次遇到与上面完全相同的代码,除了作者使用 bytestream.read(8)
而不是 bytestream.read(16)
或者很可能是任何其他值。挖掘文件 character-by-character 显示没有可辨别的模式来确定 header 字符的长度。
换句话说,如何 确定要在 read
函数调用中使用的参数? 或者如何知道 header 个 gzip-compressed 文件中的字符?
我的猜测是它与字节有关,但在搜索文档和在线参考资料后我无法确认。
可重现的细节
我的假设是,经过无数小时的故障排除后,前 16 个字符代表某种 header 或 meta-data。所以该代码的第一行是跳过 16 个字符并将剩余的字符存储在名为 buf
的变量中。但是,通过深入研究数据,我发现无法确定为什么或如何选择值 16。我已经逐个字符地读取字节,也尝试读取+将它们转换为 np.float
,但是没有明显的模式表明 meta-data 在第 16 个字符处结束,实际数据从17号。
以下代码从 this website 中读取数据并提取前 30 个字符。请注意,在 header 行 "ends"(显然是第 16 行,在 \x1c` 第二次出现之后)和数据开始的地方是无法辨认的:
import gzip
import numpy as np
train_data_filename = 'data_input/train-images-idx3-ubyte.gz'
IMAGE_SIZE = 28
NUM_CHANNELS = 1
def extract_data(filename, num_images):
with gzip.open(filename) as bytestream:
first30 = bytestream.read(30)
return first30
first30= extract_data(train_data_filename, 10)
print(first30)
# returns: b'\x00\x00\x08\x03\x00\x00\xea`\x00\x00\x00\x1c\x00\x00\x00\x1c\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'
如果我们修改代码以将它们转换为 np.float32
,这样所有字符现在都是数字(浮点),同样没有明显的模式来区分 header / meta-data 结束和数据开始的地方。
任何参考或建议将不胜感激!
从代码片段中,bytestream.read(16)
读取或跳过字节流的前 16 个字节。当您引用 read() 从流中读取最多 n 个字符时,它确实这样做了,但似乎 python 将单个字符存储在 1 个字节中,使 16 个字符占用 16 个字节。
查看有关字符和字节的更多信息https://pymotw.com/3/gzip/#reading-compressed-data
该代码片段主要对 buf 的内容感兴趣,跳过了流的前 16 个字节。要了解如何 确定 进入第一个 bytestream.read()
的参数,也就是确定要跳过压缩图像文件的多少字节,我们必须了解其余代码的作用。特别是,我们正在读取什么文件以及我们试图用 numpy(?) 库完成什么(将 rgb 图像保存在一维 numpy 数组中?)。
我绝对不是图像处理方面的专家,但 bytestream.read(16)
似乎是处理一些独特的压缩图像文件的独特问题的独特解决方案。因此,如果不查看更多代码和理解代码片段背后的更多逻辑,就很难判断如何确定要跳过多少字节。
从 gzip 的角度来看,它返回给您的所有内容都是数据。 没有元数据或 gzip-specific header 内容添加到该数据流,因此不需要任何算法来确定 gzip 有多少内容添加到前面到那个流:它前置的字节数是零。
向下滚动到您链接的页面底部;有一个 header 标题为 MNIST 数据库的文件格式。
该格式规范准确地告诉您格式是什么,以及每个 header 使用了多少字节。具体每个文件中的前四项描述如下:
0000 32 bit integer 0x00000803(2051) magic number
0004 32 bit integer 60000 number of images
0008 32 bit integer 28 number of rows
0012 32 bit integer 28 number of columns
因此,如果您想跳过所有这四项,您需要从顶部去掉 16 个字节。
在 Python 中使用 gzip
库时,我经常会遇到以如下形式使用 .read()
函数的代码:
with gzip.open(filename) as bytestream:
bytestream.read(16)
buf = bytestream.read(
IMAGE_SIZE * IMAGE_SIZE * num_images * NUM_CHANNELS
)
data = np.frombuffer(buf, dtype=np.uint8).astype(np.float32)
虽然我熟悉上下文管理器模式,但我很难真正理解 with
上下文管理器中的第一行代码到底在做什么。
这是 read()
函数的文档:
Read at most n characters from stream.
Read from underlying buffer until we have n characters or we hit EOF. If n is negative or omitted, read until EOF.
如果是这种情况,第一行 bytestream.read(16)
的功能作用必须是读取并因此跳过前 16 个字符,大概是因为它们充当 meta-data 或 header.但是,当我有一些图像时,我怎么知道使用 16
作为 read
调用的参数,而不是 32、8 或 64?
我记得有很多次遇到与上面完全相同的代码,除了作者使用 bytestream.read(8)
而不是 bytestream.read(16)
或者很可能是任何其他值。挖掘文件 character-by-character 显示没有可辨别的模式来确定 header 字符的长度。
换句话说,如何 确定要在 read
函数调用中使用的参数? 或者如何知道 header 个 gzip-compressed 文件中的字符?
我的猜测是它与字节有关,但在搜索文档和在线参考资料后我无法确认。
可重现的细节
我的假设是,经过无数小时的故障排除后,前 16 个字符代表某种 header 或 meta-data。所以该代码的第一行是跳过 16 个字符并将剩余的字符存储在名为 buf
的变量中。但是,通过深入研究数据,我发现无法确定为什么或如何选择值 16。我已经逐个字符地读取字节,也尝试读取+将它们转换为 np.float
,但是没有明显的模式表明 meta-data 在第 16 个字符处结束,实际数据从17号。
以下代码从 this website 中读取数据并提取前 30 个字符。请注意,在 header 行 "ends"(显然是第 16 行,在 \x1c` 第二次出现之后)和数据开始的地方是无法辨认的:
import gzip
import numpy as np
train_data_filename = 'data_input/train-images-idx3-ubyte.gz'
IMAGE_SIZE = 28
NUM_CHANNELS = 1
def extract_data(filename, num_images):
with gzip.open(filename) as bytestream:
first30 = bytestream.read(30)
return first30
first30= extract_data(train_data_filename, 10)
print(first30)
# returns: b'\x00\x00\x08\x03\x00\x00\xea`\x00\x00\x00\x1c\x00\x00\x00\x1c\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'
如果我们修改代码以将它们转换为 np.float32
,这样所有字符现在都是数字(浮点),同样没有明显的模式来区分 header / meta-data 结束和数据开始的地方。
任何参考或建议将不胜感激!
从代码片段中,bytestream.read(16)
读取或跳过字节流的前 16 个字节。当您引用 read() 从流中读取最多 n 个字符时,它确实这样做了,但似乎 python 将单个字符存储在 1 个字节中,使 16 个字符占用 16 个字节。
查看有关字符和字节的更多信息https://pymotw.com/3/gzip/#reading-compressed-data
该代码片段主要对 buf 的内容感兴趣,跳过了流的前 16 个字节。要了解如何 确定 进入第一个 bytestream.read()
的参数,也就是确定要跳过压缩图像文件的多少字节,我们必须了解其余代码的作用。特别是,我们正在读取什么文件以及我们试图用 numpy(?) 库完成什么(将 rgb 图像保存在一维 numpy 数组中?)。
我绝对不是图像处理方面的专家,但 bytestream.read(16)
似乎是处理一些独特的压缩图像文件的独特问题的独特解决方案。因此,如果不查看更多代码和理解代码片段背后的更多逻辑,就很难判断如何确定要跳过多少字节。
从 gzip 的角度来看,它返回给您的所有内容都是数据。 没有元数据或 gzip-specific header 内容添加到该数据流,因此不需要任何算法来确定 gzip 有多少内容添加到前面到那个流:它前置的字节数是零。
向下滚动到您链接的页面底部;有一个 header 标题为 MNIST 数据库的文件格式。
该格式规范准确地告诉您格式是什么,以及每个 header 使用了多少字节。具体每个文件中的前四项描述如下:
0000 32 bit integer 0x00000803(2051) magic number
0004 32 bit integer 60000 number of images
0008 32 bit integer 28 number of rows
0012 32 bit integer 28 number of columns
因此,如果您想跳过所有这四项,您需要从顶部去掉 16 个字节。