每日一题
leetcode-192.统计词频
写一个 bash 脚本以统计一个文本文件 words.txt 中每个单词出现的频率。
为了简单起见,你可以假设:
- words.txt只包括小写字母和 ' ' 。
- 每个单词只由小写字母组成。
- 单词间由一个或多个空格字符分隔。
示例:
假设 words.txt 内容如下:
the day is sunny the the
the sunny is is
你的脚本应当输出(以词频降序排列):
the 4
is 3
sunny 2
day 1
解法
-
将文件转行成一行;(方便后续读入到数组中)
-
通过read将一行读入单词数组words中
-
创建词频数组cnts,数组下标为词频,数组值为单词
-
遍历单词数组
- 单词word如果已经统计的成词频数组中,则continue;
- 否则再次遍历单词数组words,统计word词频,并且写入到词频数组中
-
逆序打印词频数组cnts
- 从尾部遍历词频数组,如果词频数组下标对应值为空,则忽略;
#!/bin/sh
# echo "begin read file: "
# 注意,filename变量赋值时,不能有空格
filename='/home/heaven/script/words.txt'
words=""
# 将文件都转换成一行
echo "--------------将文件都转换成一行--------------"
while read myline
do
words="$words $myline"
done < $filename
echo $words
echo "----------------开始拆分字符串----------------"
# 将空格设置为分隔符
IFS=' '
echo "-----将单词都读取到数组中, 并由IFS分配分隔符-----"
read -ra wordArr <<< "$words"
# 遍历数组中所有的元素
for i in "${wordArr[@]}";
do
echo "$i"
done
length=${#wordArr[*]}
echo "---------总共有单词 $length 个---------------"
# 遍历数组的每个元素,统计每个元素出现的次数,存入数组中
## 先定义计数数组
cntArray[0]=''
for word in "${wordArr[@]}";
do
cnt=0
flag=false
for item in "${cntArray[@]}";
do
# echo "item: $item word: $word"
if [ "$item" = "$word" ]; then
flag=true;
break;
fi
done
if [ "$flag" = "true" ]; then
continue;
fi
for item in "${wordArr[@]}";
do
if [ "$item" = "$word" ]; then
cnt=$(($cnt + 1))
fi
done
cntArray[$cnt]=$word
# echo "word: $word, cnt: $cnt"
done
echo "--------------以词频逆序排序------------"
for (( i=${#cntArray[*]}; i > 0; i = i - 1 ));do
if [ "${cntArray[$i]}" != "" ]; then
echo "${cntArray[$i]} $i"
fi
done
echo "end"
待优化点
- 时间复杂度过高;暴力解法,前时间复杂度为n2,是否可优化;
- 输入限制;当前输入只支持每个单词出现的频率都是唯一的;
- 阅读linux指令实现,改为一个指令,支持参数配置