【问题标题】:Read X Number of Bytes from Pipe in Perl [closed]在 Perl 中从管道中读取 X 字节数 [关闭]
【发布时间】:2019-10-03 16:18:20
【问题描述】:

在 Perl 中从管道中读取 x 个二进制字节的最佳方法是什么?使用 sysread 仅返回 8K 字节。在继续脚本的其余部分之前,我需要从管道中读取大约 1GB 的字节。显然,我可以自己将所有 8K 块组合在一起,但我希望这样的东西已经存在,而不必自己编写代码。

【问题讨论】:

  • 如果您指定的长度尚不可用,read 函数将等待。与 sysread 不同,它还将尊重句柄上的层(例如 :encoding 层或 Windows 上的 :crlf 转换),如果存在 binmode,您可以从句柄中删除这些层。
  • 我尝试使用 read,不幸的是它也从管道返回 8K。
  • 也许它不是可移植的,它会在所有操作系统和管道上执行此操作。我认为循环直到你有你想要的输入量是最好的选择。
  • @Grinnz, Re "如果您指定的长度尚不可用,则读取函数将等待",绝不保证会这样做。事实上,当它是一个管道时,它并不总是等待。 What is the difference between read and sysread?
  • 这是怎么回事?投票重新开放。

标签: perl pipe


【解决方案1】:

使用 sysread 只返回 8K 字节

不太具体,它会返回所有可用字节,直到提供的最大值。 (如果管道中没有,它将等待一些到达。)

在继续脚本的其余部分之前,我需要从管道中读取大约 1GB 的字节。

我不确定是否有办法检查管道中等待的字节数,但没有系统具有可以容纳 1 GB 或 1 GiB 的管道。循环阅读即可。

use constant TO_READ => 1000*1000*1000;  # Or 1024*1024*1024?

my $buf = '';
while (length($buf) < TO_READ) {
   my $rv = sysread($fh, $buf, TO_READ-length($buf), length($buf));
   defined($rv)
      or die("Can't read from file: $!\n");
   $rv
      or die("Can't read from file: Premature EOF\n");
}

您也可以轻松使用readWhat is the difference between read and sysread?

【讨论】:

  • 请注意,sysread 会将缓冲区扩展到足够大以容纳请求的字节数,而不管实际读取了多少字节。这意味着上述程序不会不断地扩展缓冲区,最终只会过度分配 8 个字节(而不是浪费多达 200 MB)。
猜你喜欢
  • 1970-01-01
  • 2012-03-27
  • 1970-01-01
  • 1970-01-01
  • 2018-07-20
  • 1970-01-01
  • 1970-01-01
  • 2013-08-11
  • 1970-01-01
相关资源
最近更新 更多