6

我正在尝试决定在我的代码中使用的最佳内部接口,特别是围绕如何处理文件内容。实际上,文件内容只是二进制数据,因此字节足以表示它们。

我将文件存储在不同的远程位置,所以有几个不同的读写类。我正在尝试找出用于我的功能的最佳界面。最初我使用的是文件路径,但这不是最理想的,因为这意味着磁盘总是被使用(这意味着很多笨拙的临时文件)。

代码中有几个区域具有相同的要求,并且会直接使用从该接口返回的任何内容。因此,我选择的任何抽象都会涉及到相当多的代码。

使用 BytesIO 与字节的各种权衡是什么?

def put_file(location, contents_as_bytes):
def put_file(location, contents_as_fp):
def get_file_contents(location):
def get_file_contents(location, fp):

玩弄我发现使用类似文件的接口(BytesIO 等)需要一些管理开销seek(0)等方面。这引发了如下问题:

  • seek是在开始之前更好,还是在完成之后更好?
  • seek是从文件所在的位置开始操作还是从文件所在的位置开始操作?
  • tell()应该保持这个位置吗?
  • 看着类似的东西shutil.copyfileobj不会做任何寻求

我发现使用类似文件的接口的一个优点是它允许在您检索数据时传入 fp 以写入。这似乎提供了很大的灵活性。

def get_file_contents(location, write_into=None):
    if not write_into:
        write_into = io.BytesIO()

    # get the contents and put it into write_into

    return write_into

get_file_contents('blah', file_on_disk)
get_file_contents('blah', gzip_file)
get_file_contents('blah', temp_file)
get_file_contents('blah', bytes_io)
new_bytes_io = get_file_contents('blah')
# etc

在 python 中设计接口时,是否有充分的理由更喜欢 BytesIO 而不是仅使用固定字节?

4

1 回答 1

3

对象的好处io.BytesIO是它们实现了一个通用的接口(通常称为“类文件”对象)。BytesIO对象有一个内部指针(其位置由 返回tell()),每次调用read(n)指针都会增加n字节。前任。

import io

buf = io.BytesIO(b'Hello world!')
buf.read(1) # Returns b'H'

buf.tell()  # Returns 1
buf.read(1) # Returns b'e'

buf.tell() # Returns 2

# Set the pointer to 0.
buf.seek(0)
buf.read() # This will return b'H', like the first call.

在您的用例中,bytes对象和io.BytesIO对象可能都不是最佳解决方案。他们会将文件的完整内容读入内存。

相反,您可以查看tempfile.TemporaryFilehttps://docs.python.org/3/library/tempfile.html)。

于 2015-02-25T10:44:03.543 回答