![一个单词中字母出现的次数?](https://linux22.com/image/59648/%E4%B8%80%E4%B8%AA%E5%8D%95%E8%AF%8D%E4%B8%AD%E5%AD%97%E6%AF%8D%E5%87%BA%E7%8E%B0%E7%9A%84%E6%AC%A1%E6%95%B0%EF%BC%9F.png)
我想找出一个单词中每个字母出现的次数。例如
输入aabbbddd
输出
a@2 b@3 c@0 d@3
如何使用 shell 脚本执行此操作?
答案1
您可以使用sed
、uniq
和sort
:
$ echo -n "aabbbddd" | sed 's/\(.\)/\1\n/g'| sort | uniq -c
2 a
3 b
3 d
上面的代码使用sed
每个字符并将其替换为自身+换行符 ( \n
)。现在,每个字符都在换行符上(并已排序),您可以使用它uniq -c
来计算字符数。
笔记:此方法不会显示其间出现次数为零的任何字符。
或者显示每个字母的计数
$ s="aabbbddd"; for i in {a..z}; do
v=$(echo -n "$s" | grep -oi $i | wc -l); echo "$i : $v"; done
a : 2
b : 3
c : 0
d : 3
e : 0
f : 0
g : 0
h : 0
i : 0
j : 0
k : 0
l : 0
m : 0
n : 0
o : 0
p : 0
q : 0
r : 0
s : 0
t : 0
u : 0
v : 0
w : 0
x : 0
y : 0
z : 0
这是通过循环遍历字母表的所有字母来实现的:
for i in {a..z}; do .... ; done
循环的每次迭代我们都会通过字符串 grep 查找特定字符,并使用-o
选项grep
仅返回这些匹配项。然后,我们计算wc -l
找到的每个字母出现的次数,并将其存储在变量中$v
。然后我们显示每次迭代:
echo "$i : $v"
笔记:这种方法可以处理乱序的字符串。
答案2
这些解决方案不区分大小写:
start cmd:> echo aabbbddd |
awk -v FS= '{for (i=1;i<=NF;i++) a[tolower($i)]++;};
END {for (key in a) print key ": " a[key];}'
a: 2
b: 3
d: 3
或者对于完整的字母表:
start cmd:> echo Aabbbddd |
awk -v FS= '{for (i=1;i<=NF;i++) a[tolower($i)]++;};
END {chars="abcdefghijklmnopqrstuvwxyz";
for (i=1;i<27;i++) { key=substr(chars,i,1);print key ": " a[key]};}'
a: 2
b: 3
c:
d: 3
e:
f:
g:
h:
i:
j:
k:
l:
m:
n:
o:
p:
q:
r:
s:
t:
u:
v:
w:
x:
y:
z:
答案3
仅使用 shell(对于短字符串更快):
#! /bin/bash -
input=${*:-'aabbbddd'}
tmp=$input
arr=()
maxlen=0
maxchar=''
while ((${#tmp})); do
firstchar=${tmp:0:1}
next=${tmp//"$firstchar"}
len=$((${#tmp}-${#next}))
arr+=("$firstchar: $len")
if ((maxlen<len)); then
maxlen=$len
maxchar=$firstchar
fi
tmp=$next
done
printf '%s\n' "${arr[@]}"
echo "The char \"$maxchar\" appear $maxlen times in \"$input\""
称为:
$ ./script
a@2 b@3 d@3
The char "b" appear 3 times in "aabbbddd"