gpt4 book ai didi

bash - 流过滤大量由标准输入中的行号指定的行

转载 作者:行者123 更新时间:2023-12-04 16:23:56 24 4
gpt4 key购买 nike

我有一个巨大的 xz 压缩文本文件 huge.txt.xz,其中包含数百万行,太大而无法在未压缩的情况下保存 (60GB)。

我想从那个巨大的文本文件中快速过滤/选择大量行(~1000s)到文件filtered.txt中。例如,要选择的行号可以在单独的文本文件 select.txt 中指定,格式如下:

10
14
...
1499
15858

总的来说,我设想的 shell 命令如下,其中“TO BE DETERMINED”是我正在寻找的命令:

xz -dcq huge.txt.xz | "TO BE DETERMINED" select.txt >filtered.txt

我设法从一个密切相关的问题中找到了一个 awk 程序,它几乎可以完成这项工作 - 唯一的问题是它需要一个文件名而不是读取来自标准输入。不幸的是,我并不真正了解 awk 脚本,也不了解足够的 awk 来以这种方式改变它以在这种情况下工作。

这是目前有效的方法,缺点是有一个 60GB 的文件存在而不是流式传输:

xz -dcq huge.txt.xz >huge.txt
awk '!firstfile_proceed { nums[$1]; next }
(FNR in nums)' select.txt firstfile_proceed=1 >filtered.txt

灵感:https://unix.stackexchange.com/questions/612680/remove-lines-with-specific-line-number-specified-in-a-file

最佳答案

保持OP当前的想法:

xz -dcq huge.txt.xz | awk '!firstfile_proceed { nums[$1]; next } (FNR in nums)' select.txt firstfile_proceed=1 -

-(在行尾)告诉 awk 从 stdin 读取(在本例中是 xz 的输出)被管道传输到 awk 调用)。

另一种方法(替换所有上述代码):

awk '
FNR==NR { nums[$1]; next } # process first file
FNR in nums # process subsequent file(s)
' select.txt <(xz -dcq huge.txt.xz)

删除评论并缩减为“一行”:

awk 'FNR==NR {nums[$1];next} FNR in nums' select.txt <(xz -dcq huge.txt.xz)

添加一些逻辑来实现 Ed Morton 的评论(一旦 FNR > select.txt 中的最大值就退出处理):

awk '
# process first file

FNR==NR { nums[$1]
maxFNR= ($1>maxFNR ? $1 : maxFNR)
next
}

# process subsequent file(s):

FNR > maxFNR { exit }
FNR in nums
' select.txt <(xz -dcq huge.txt.xz)

注意事项:

  • 请记住,我们正在谈论扫描数百万行输入 ...
  • FNR > maxFNR 显然会为整体操作增加一些 cpu/处理时间(尽管时间少于 FNR in nums)
  • 如果操作通常需要从文件的最后 25% 中提取行,那么 FNR > maxFNR 可能不会提供什么好处(并且可能会减慢操作速度)
  • 如果操作通常在文件的前 50% 中找到所有需要的行,那么 FNR> maxFNR 可能值得 cpu/处理时间来避免扫描整个输入流(再一次,对整个文件的 xz 操作可能是最大的时间消耗者)
  • 最终结果:额外的 NFR > maxFNR 测试可能会加快/减慢整个过程,具体取决于在典型运行中需要处理多少输入流; OP 需要运行一些测试以查看整体运行时间是否存在(明显的)差异

关于bash - 流过滤大量由标准输入中的行号指定的行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/69049498/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com