ple*_*elp 3 awk text-processing
我想算辅音的出现在多个文件,但我想对每个文件进行单独计算出现的次数。我用
awk -v FS="" '{for ( i=1;i<=NF;i++){if($i ~/[bcdfghjklmnpqrtsvwxyzBCDEFGHJKLMNPQRTSVWXYZ]/) count_c++}} END {print FILENAME,count_c}' file1 file2
Run Code Online (Sandbox Code Playgroud)
file1 看起来像这样:
bac Dfeg
k87 eH
tRe
rt up
Run Code Online (Sandbox Code Playgroud)
file2 看起来像这样:
hi
rt2w
Prt
Run Code Online (Sandbox Code Playgroud)
但它会打印两个文件的出现次数 (output= file2 19)。我怎么能改变这个,所以输出会是这样的:
file1 12
file2 7
Run Code Online (Sandbox Code Playgroud)
使用 GNU awk 处理 ENDFILE 和 IGNORECASE:
$ awk -v IGNORECASE=1 '
{ cnt += ( gsub(/[[:alpha:]]/,"&") - gsub(/[aeiou]/,"&") )}
ENDFILE { print FILENAME, cnt+0; cnt=0 }
' file1 file2
file1 12
file2 7
Run Code Online (Sandbox Code Playgroud)
或使用任何 POSIX awk:
$ awk '
{ lc=tolower($0); cnt[FILENAME] += (gsub(/[[:alpha:]]/,"&",lc) - gsub(/[aeiou]/,"&",lc)) }
END { for (i=1; i<ARGC; i++) print ARGV[i], cnt[ARGV[i]]+0 }
' file1 file2
file1 12
file2 7
Run Code Online (Sandbox Code Playgroud)
如果您只想计算特定字符 b、c、d 等而不是所有不是 aeiou 的字母字符,那么只需将( gsub(/[[:alpha:]]/,"&") - gsub(/[aeiou]/,"&") )上面更改为gsub(/[bcdfghjklmnpqrtsvwxyz]/,"&"))
请注意,与在FNR==1子句中打印结果的任何方法不同,上述两个脚本都将通过打印文件名和 0 作为计数来正确处理空文件。
还要注意cnt+0第一个脚本中的 -如果第一个文件为空,则+0确保打印的值将是数字0而不是空字符串。
如果相同的文件名可以在输入中多次出现,那么FNR==1{cnt[FILENAME]=0}如果您希望它多次输出,则添加到脚本的开头,或者if (!seen[ARGV[i]]++) { ... }如果您只想输出一次,则在 END 部分的打印周围添加。
请参阅https://unix.stackexchange.com/a/642372/133219以获取对元音计数的后续问题的回答。