【问题标题】:Why is StringIO object slower than real file object?为什么 StringIO 对象比真实文件对象慢?
【发布时间】:2014-10-24 05:05:25
【问题描述】:

我正在查看StringIO 的来源,上面写着一些注释:

  1. 使用真实文件通常更快(但不太方便)
  2. C 中还有一个更快的实现,称为cStringIO,但是 它不可子类化。

StringIO 就像一个内存文件对象, 为什么它比真正的文件对象慢?

【问题讨论】:

    标签: python stringio cstringio


    【解决方案1】:

    不是实际上是关于 Python 的解释性质:BytesIO 在 Python* 中实现,与 StringIO 相同,但仍然优于文件 I/O。

    事实上,StringIOStringIO 的理想用例(单次写入空缓冲区的开头)下比文件 I/O 快。实际上,如果写入足够大,它甚至会击败cStringIO。请参阅我的问题here

    那么为什么StringIO 被认为是“慢”? StringIO 的真正问题是得到不可变序列的支持,无论是str 还是unicode。如果你只写一次,这很好,很明显。但是,正如tdelaney's answer 对我的问题所指出的那样,它在写入随机位置时会减慢一吨(例如,10-100 倍),因为每次在中间写入时,它都必须复制整个支持序列。

    BytesIO 没有这个问题,因为它由(可变的)bytearray 支持。同样,无论cStringIO 做什么,它似乎都更容易处理随机写入。我猜它在内部打破了不变性规则,因为 C 字符串是可变的。

    * 无论如何,_pyio 中的版本是。 io 中的标准库版本是用 C 编写的。

    【讨论】:

    • 很好的答案,竖起大拇指!
    【解决方案2】:

    从源代码上看不一定很明显,但是 python 文件对象是直接构建在 C 库函数上的,可能有一小层 python 来呈现 python 类,甚至是 C 包装器来呈现 python 类。本机 C 库将被高度优化以从磁盘读取字节和块。 python StringIO 库都是原生 python 代码——比原生 C 代码慢。

    【讨论】:

    • 好的 - 重新阅读这个问题是矛盾的。需要进行小修改 - 完成:-)
    • 对不起我的英语不好,我的意思是look through,而不是look for
    【解决方案3】:

    Python 的文件处理is implemented entirely in C。这意味着它的速度非常快(至少与原生 C 代码的数量级相同)。

    但是,StringIO 库是用 Python 编写的。因此,模块本身会被解释,并带有相关的性能损失。

    如您所知,还有另一个模块 cStringIO,带有 similar interface,您可以在对性能敏感的代码中使用它。 这不是子类的原因是因为它是用 C 编写的。

    【讨论】:

    • 感谢您的回答。
    • @sapi - BytesIO 有类似的东西吗?
    猜你喜欢
    • 2016-05-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-08-09
    • 2019-05-21
    • 1970-01-01
    相关资源
    最近更新 更多