【问题标题】:Is seek to 0 in an opened file faster than close the file then open it again?在打开的文件中寻找 0 是否比关闭文件然后再次打开它更快?
【发布时间】:2020-01-18 03:56:57
【问题描述】:

假设我已经打开了一个文件。我想给它写一些新内容(覆盖文件中的任何旧内容)。无论文件大小如何,我都希望此操作能够高效运行。

在已经打开的文件中寻找 0 是否比关闭文件然后再次打开更快?

【问题讨论】:

  • 我认为这值得一试,但我无法想象关闭和打开可能比仅通过搜索更改文件指针更快。
  • 在与文件描述符相关的内部结构(严格来说是打开文件描述)中将数字更改为零比关闭文件要快得多,更不用说关闭和重新打开文件了。
  • 在我看来,这将是您可以使用现有文件自己测试的东西。你不能自己写一个快速的基准测试吗?

标签: c file


【解决方案1】:

在我们谈论哪个更快之前,首先我们必须证明它们是等价的。他们不是。

仅寻求 0 不足以确保所有内容都被覆盖。如果新内容更短怎么办?你必须寻找和截断才能确定。

没有截断打开文件的标准方法。 POSIX 有ftruncate,Windows 有SetEndOfFilefopen(filename, "w") 是标准的 C,所以 seek 和 truncate 会带来兼容性问题。

请参阅 Is there a guaranteed and safe way to truncate a file from ANSI C FILE pointer?How to truncate a file in C?


文件删除还有一个细微的差别。在 Unix 上,如果您删除一个文件,任何打开的文件句柄都会保持打开状态。数据会一直保留到所有文件句柄都关闭为止。这通常被利用来拥有安全的临时文件:打开临时文件进行读写,立即删除该文件,然后继续读写打开的文件句柄。不可见的临时文件。

假设您的文件在文件句柄打开时被删除。如果您查找并截断,您仍在使用相同的数据,但没有文件。如果您 fopen 您正在写入一个新文件。这可能会影响行为和安全。

文件重命名也有类似的问题。如果您的文件在文件句柄打开时被重命名,则查找和截断将与重命名的文件一起使用 (there are various non-portable ways to get the filename from a file handle)。 fopen 将使用旧名称打开一个文件。


哪个更快?可能会寻找并截断。 fopen 无论如何都必须这样做,加上定位与文件名相关的数据、检查权限等的开销......

您可以很容易地对此进行基准测试。您还可以使用strace 或您的操作系统的等效项来查看底层系统调用。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-01-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多