我需要在.csv文件中找到最常见的10个单词。文件的结构使得每一行都包含逗号分隔的单词。如果同一个单词在同一行中重复多次,则应将其计算为一个单词。因此,在下面的示例中:
green,blue,blue,yellow,red,yellow
red,blue,green,green,green,brown
绿色、蓝色和红色应算作2,黄色和棕色应算作1。
我知道以前也有人问过类似的问题,其中一个解决办法是:
<file.csv tr -c '[:alnum:]' '[\n*]' | sort|uniq -c|sort -nr|head -10
但这将计算单词出现在同一行中的时间,如下所示:
4 green
3 blue
2 yellow
2 red
1 brown
这并不是我真正需要的。有什么帮助吗?另外,我将感谢对这个命令的简短解释,以及为什么我在类似的问题中找到的命令没有做我需要的事情。
发布于 2020-06-02 09:49:23
使用GNU grep
或兼容:
$ grep -nEo '\w+' file.csv|sort -u|cut -d: -f2-|sort|uniq -c|sort -k1rn|head
2 blue
2 green
2 red
1 brown
1 yellow
发布于 2020-06-03 10:07:13
我假设这些单词不包含任何嵌入的逗号,并且它们没有被引用,或者每个单词都被连贯地引用(例如,"foo",bar,"foo"
很好,但是"foo",bar,foo
会认为"foo"
和foo
是不同的,"foo,bar",qux
是两个单词)。否则,您需要一个适当的CSV处理工具。
我还假设空的“单词”不会出现在数据中,也不重要。
在这些假设下,您可以使用sed删除每一行上的重复单词,而不会造成太大的痛苦。我是这样做的:首先在行的开头和结尾加上逗号,在行内重复逗号,这样每个单词都被“属于”它的两边的逗号完全包围。然后删除行上重复的逗号括起来的单词。在此之后,您可以使用计划中的策略将逗号转换为换行和计数重复行。
sed -e 's/,/,,/g; s/^/,/; s/$/,/; :s; s/\(,[^,][^,]*,\)\(.*\)\1/\1\2/; t s' |
tr , '\n' |
sort | uniq -c |
sort -nr | head
发布于 2020-06-19 23:08:05
我会用Python来做这个。之所以如此,是因为代码易于阅读和修改。
import collections
import operator
import sys
word_count = collections.Counter()
with open(sys.argv[1]) as f:
for l in f:
words = set(l.strip().split(','))
word_count.update(words)
words_kv = word_count.items()
words_kv = sorted(words_kv, key = operator.itemgetter(0)) # First sort alphabetically.
words_kv = sorted(words_kv, key = operator.itemgetter(1), reverse = True) # Then sort by most common.
# Then end result is a list that is sorted first by most common then alphabetically. The reason this works is because sorting is stable in Python according to: https://docs.python.org/3/howto/sorting.html#sort-stability-and-complex-sorts
for word, count in words_kv:
print(count, word)
输出:
2 blue
2 green
2 red
1 brown
1 yellow
https://unix.stackexchange.com/questions/590303
复制相似问题