实践目标:
1、掌握单词到数字ID的映射技术;
2、编写创建字典的程序。
字典程序编码
分词程序将文本数据切分为单词序列,还需要对这些单词序列做进一步处理,将单词序列转换为字典,字典是一个集合对象,key是单词,value是一个整数ID,该整数ID在词典中唯一,它唯一标识词典中的一个单词。
例如有下面的单词序列w1和w2:
w1:{五朵,金花,齐,上阵}
w2:{上阵,父子,兵}
将w1和w2单词序列转换为字典对象:
dictionary = {"五朵":0,"金花":1,"齐":2,"上阵":3,"父子":4,"兵":5}
单词序列转换为字典对象,是文本转换为向量空间模型的一个重要方法,文本中的每个单词都被赋予一个唯一的数字ID,通过该数字ID,将单词映射为数值,我们就可以使用数学方法来对文本内容进行处理和分析。
字典处理程序流程图如下:
程序首先初始化字典数据,在生成字典的过程中,使用两层循环,外层循环遍历文档集,内层循环遍历文档内的单词序列,若单词没在字典中,建立单词和数字ID键值对,将键值对添加到单词,并初始化单词在所有文档中的出现频率,若单词已在字典中,统计单词在所有文档出现的频率。
Pythoy代码:
"""
模块:字典
功能:
1、建立和存储单词与整数ID的映射
2、单词去重
"""
class Dictionary():
def __init__(self, documents=None):
# 存储单词到id的映射
self.token2id = {}
# 存储id到单词的映射
self.id2token= {}
# 存储单词id在所有文档中出现的次数
self.dfs = {}
# 词典中的文档数量
self.num_docs = 0
# 字典单词总数
self.num_pos = 0
def __len__(self):
"""
返回token2id字典长度
"""
return len(self.token2id)
def add_documents(self,documents):
"""
1、documents:多个文档
2、一个文档是一个单词序列
3、处理单词序列,添加到字典
4、单词序列去重
"""
# 获取当前字典单词数量
self.num_pos = len(self.token2id)
# 遍历documents:
for text in documents:
for token in text:
# token映射为数字ID
if token in self.token2id:
# 统计token在所有文档出现的次数
self.dfs[self.token2id[token]] += 1
else:
# token映射到self.num_pos
self.token2id[token] = self.num_pos
self.dfs[self.token2id[token]] = 1
self.num_pos += 1
# 更新文档数量
self.num_docs += len(documents)
# 返回数字ID到单词的映射字典
def get_id2token(self):
self.id2token = dict([(value,key) for (key,value) in self.token2id.items()])
return self.id2tokenDictionary类属性token2id是字典结构,存储单词(token)到数字ID的映射,token是字典的key,数字ID是字典的value,数字ID由类属性num_pos指定,num_pos的值为当前字典的长度。字典数据样例如下:
{'计算机': 0, 'Java编程': 1, 'C++编程': 2, '编程': 3}
Dictionary类属性id2token是字典结构,是token2id的反向映射,即数字ID到单词的映射,该字典数据仅在请求时生成。字典数据样例如下:
{0: '计算机', 1: 'Java编程', 2: 'C++编程', 3: '编程'}
Dictionary类属性dfs是字典结构,存储单词在所有文档出现的频率,字典的key为单词的数字ID,字典的value为该单词在所有文档出现的频率。字典数据样例如下:
{0: 3, 1: 1, 2: 2, 3: 4}
Dictionary类属性num_docs是整数类型,存储文档数量。
Dictionary类属性num_pos是整数类型,存储token2id字典内的单词数量,用于产生不重复的数字ID。
验证字典程序
字典程序编写完成后,还需要验证字典程序是否能正常工作。编写一个测试程序,建立测试数据,调用字典程序建立测试数据的字典。在项目的test目录下建立particlple_test.py文件。
程序清单 particlple_test.py
# 字典测试程序
#导入字典模块
from corpora.dictionary import Dictionary
# 创建字典
dictionary = Dictionary()
# 建立测试数据
texts = [["计算机","Java编程","C++编程","编程","计算机","编程"],
["Python编程","计算机","编程","语言"],
["C++编程","编程","课程"]]
# 建立测试数据的字典
dictionary.add_documents(texts)
print('=================dictinary=============')
print('单词到数字ID的映射(token2id):',dictionary.token2id)
print('数字ID到单词的映射(id2token):',dictionary.get_id2token())
print('单词在所有文档中出现的频率(dfs):',dictionary.dfs)
print('处理的文档数量(num_docs):',dictionary.num_docs)
print('字典的单词总数(num_pos):',dictionary.num_pos)
print('=================dictinary=============')测试程序执行结果:
=================dictinary=============
单词到数字ID的映射(token2id): {'计算机': 0, 'Java编程': 1, 'C++编程': 2, '编程': 3, 'Python编程': 4, '语言': 5, '课程': 6}
数字ID到单词的映射(id2token): {0: '计算机', 1: 'Java编程', 2: 'C++编程', 3: '编程', 4: 'Python编程', 5: '语言', 6: '课程'}
单词在所有文档中出现的频率(dfs): {0: 3, 1: 1, 2: 2, 3: 4, 4: 1, 5: 1, 6: 1}
处理的文档数量(num_docs): 3
字典的单词总数(num_pos): 7
=================dictinary=============