Rime 四叶草方案字频分布分析
说到输入法当然要用开源的了,不然谁知道自己的打字记录会在云端保留多久。我在用的是 Rime 输入法+四叶草拼音输入方案+小鹤双拼,不过四叶草字库里生僻字太多,翻页翻过头时就全变成无法识别的方块了(没有安装支持过于生僻字的字体)。
字的频度值越低,说明字越生僻。所以可以设置一个最低频度来控制候选词里的生僻字数。先把频度值都取出来:
awk -F\\t '$3!="" {print $3}' data/clover.base.dict.yaml > freq.txt
数据分析用 Jupyter 笔记本比较方便。安装上 VSCode 的 Jupyter 插件,在 VSCode 里选择有 seaborn 和 ipykernel 包的 Python 环境就可以开始分析了。
首先把需要的不需要的依赖都导入进来,免得后面再找。
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
然后把之前提取出的词频文件用 pandas 导入
fl = pd.read_csv('freq.txt', names=['cnt'], header=None)
df = fl['cnt']
成功后就可以开始画图分析了,先画个分布图。
sns.displot(df)
然而执行了好几分钟还没跑出来结果。回头看一眼数据,最大值 579392145,最小值 0。这个分布太散直接拿来画图确实不合理,那就取个对数试试。为了后面好过滤就以 10 为底吧。
df_log = df.transform(np.log10)
sns.displot(df_log)
这次 OK 了,可以看出个位数频度里有不少字,放大看下
df_less_than_10 = df.where(lambda x : x < 10).dropna()
sns.displot(df_less_than_10)
三万多字集中在 1 上,回到 yaml 文件里一看全是生僻字,直接过滤了吧。
df_log_main = df_log.where(lambda x : x > 1).dropna()
sns.displot(df_log_main)
这就好看多了。大部分字还是集中在 10e4 到 10e6 范围内。那就从频度 10000 往下翻看有没有需要保留的字。
$ cd data
$ less clover.base.dict.yaml
<用 ^I...$ 搜索定位到 1000 以下>
$ grep '扁' clover.base.dict.yaml
扁 bian 255939
扁 pian 661
看来保留到 600 字频应该就差不多了,剩下的要么是生僻字,要么是多音字很少见的读音。
diff --git a/src/clover-dict-gen b/src/clover-dict-gen
index 4ef8716..87b74a8 100755
--- a/src/clover-dict-gen
+++ b/src/clover-dict-gen
@@ -186,12 +186,13 @@ class DictGenerator:
return (word_count, parse_count)
- def getWordDictText(self):
+ def getWordDictText(self, min_freq = -1):
"""
生成单字的 rime 字典文本
"""
# 按频率倒序排序
word_list = [(key[0], key[1], self.word_dict[key]) for key in self.word_dict]
+ word_list = list(filter(lambda w: w[2] > min_freq, word_list))
word_list.sort(key = lambda w: w[2], reverse = True)
# 生成文本
@@ -292,7 +293,7 @@ name: %s
version: "1.0.0"
sort: by_weight
...
-""" % word_dict_name + generator.getWordDictText()
+""" % word_dict_name + generator.getWordDictText(600)
parse_dict_text = """
# Rime 字典
搞定,重新 build 一下就好了。