Linux工具 - 如何计数和列出文件中正则表达式的出现次数。

5

我有一个包含大量相似字符串的文件。我想要计算正则表达式的唯一出现次数,并显示它们是什么,例如对于该文件上的模式Profile: (\w*):

Profile: blah
Profile: another
Profile: trees
Profile: blah

我想查找三个匹配项,并返回结果:

blah, another, trees

@Stefen 我认为 NoMatch: nomatch 这一行不应该出现在结果中。请确认一下。如果是这样,请在示例中添加这样的负面字符串,以便您不会得到错误的结果。 - jkshah
2个回答

6

试试这个:

egrep "Profile: (\w*)" test.text -o | sed 's/Profile: \(\w*\)/\1/g' | sort | uniq

输出:

another
blah
trees

描述

使用带有 -o 选项的 egrep 可以在文件中获取匹配模式。

sed 只会获取捕获部分。

sort 后跟 uniq 将给出一个唯一元素列表。

要获取结果列表中的元素数量,请将命令附加上 wc -l

egrep "Profile: (\w*)" test.text -o | sed 's/Profile: \(\w*\)/\1/g' | sort | uniq | wc -l

输出:

3

+1 返回正确的列表,只有部分答案,因为它没有返回计数。 - Stefan
这个解决方案可以工作...但就我个人而言,我不喜欢grep|sed|sort|uniq四个进程的组合...如果OP想要计数,我猜wc也可以加入派对? - Kent
@Stefan 感谢您指出这一点。我正在更新帖子的描述和扩展名。 - jkshah
@Kent 我对了解简洁的解决方案很感兴趣。但就个人而言,我更喜欢简单易读的代码,而不是要记住带有单一实用程序的复杂选项组合。 - jkshah
@jkshah说实话,你的解决方案是一种复杂的命令和选项组合。想想看,“我有一个包含大量相似字符串的文件”,如果这个文件有1亿行,你需要处理多少次才能得到第一个输出呢?而要得到计数,你还要再次加倍处理次数。嗯,就像我说的,这只是我的个人意见。你的命令在这个问题的示例中确实起作用了。 - Kent
1
@Kent 嗯,我完全同意你的看法。我曾经遇到过处理大文件时的处理开销问题。但我也是一个初学者,渴望知道最优解决方案。我看到你使用了 awk,我会尝试去理解它。 - jkshah

1
awk '{a[$2]}END{for(x in a)print x}' file

将会在您的示例上进行工作

kent$  echo "Profile: blah
Profile: another
Profile: trees
Profile: blah"|awk '{a[$2]}END{for(x in a)print x}'
another
trees
blah

如果您想在输出中获得计数(3):
awk '{a[$2]}END{print "count:",length(a);for(x in a)print x }' file

使用相同的示例:

kent$  echo "Profile: blah
Profile: another
Profile: trees
Profile: blah"|awk '{a[$2]}END{print "count:",length(a);for(x in a)print x }'
count: 3
another
trees
blah

+1 非常赞同您考虑效率。尽管我认为您的答案更简洁、更高效,但其实在理解 jkshah 的答案并替换他的变量(例如正则表达式字符串)时,读者会觉得比较容易。 - Stefan
@Kent 这在添加 Nomatch: nomatch 后失败,会产生虚假通过。这里 OP 想要的是只匹配 Profile: (\w*) 的行。 - jkshah
@Kent 这个使用了正则表达式吗?我对 awk 完全不熟悉。 - jkshah
@jkshah也许你是对的。应该检查一下模式。将其添加到一行代码中会非常容易。根据所提出的示例数据,我们不需要正则表达式。 - Kent
@Kent 哈哈!基于这个示例数据的假设,我本来可以省略 grep 的 ;) sed|sort|uniq 将会起作用。 - jkshah

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