从已读取的文件句柄重新读取

18

我打开一个文件,逐行读取:

open(FH,"<","$myfile") or die "could not open $myfile: $!";
while (<FH>)
{
    # ...do something
}

程序后面我尝试重新读取文件(再次遍历文件):

while (<FH>)
{
    # ...do something
}

我发现好像文件中的控制已经到达了EOF,不会从文件的第一行开始迭代...这是默认行为吗?有什么解决方法吗?这个文件很大,我不想将它作为数组保存在内存中。所以我的唯一选择是关闭并重新打开文件吗?

2个回答

27

使用 seek 函数将文件指针回到文件开头:

seek FH, 0, 0;

或者更详细地说:

use Fcntl;
seek FH, 0, SEEK_SET;
请注意,如果您必须在输入中进行搜索,则会极大地限制您的工具的实用性,因为它永远无法用作过滤器。能够从管道中读取是非常有用的,您应该努力安排程序,使得不需要寻找。

6

你有几个选择。

  • 重新打开文件句柄
  • 使用seek将位置设置为文件开头,如William Pursell所建议的那样。
  • 使用像Tie::File这样的模块,让你将文件读取为数组,而无需将其加载到内存中。

关于Tie::File,我注意到在stackoverflow上有一个关于BerkeleyDB的评论(丢失链接) - 在读取非常大的文件时,在不将它们一次性放入RAM中的情况下。 我认为,目前使用seek足够了。再次感谢! - rajeev
1
@rajeev 这是一个非常好的模块,它从v5.7.3版本开始就是核心安装的一部分。我认为“标准”的解决方案就是简单地重新打开文件句柄。你甚至不需要先关闭文件句柄,因为这是自动完成的。 - TLP

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接