文章目录
-
- 一、文本预处理与分词
-
- [1.1 分卷处理](#1.1 分卷处理)
- [1.2 分词与停用词过滤](#1.2 分词与停用词过滤)
- [二、TF-IDF 关键词提取](#二、TF-IDF 关键词提取)
-
- [2.1 读取分词结果与向量化](#2.1 读取分词结果与向量化)
- [2.2 关键词提取与排序](#2.2 关键词提取与排序)
一、文本预处理与分词
1.1 分卷处理
首先,我们读取《红楼梦》完整文本,并依据"卷 第"标记将其拆分为多个分卷文件。过程中过滤掉与小说内容无关的电子书信息行(如"手机电子书"、"本章字数"等),确保分析数据的纯净性。
python
import os
import pandas as pd
import jieba
import re
file = open(r".\红楼梦\红楼梦.txt", encoding='utf-8')
flag = 0
juan_file = open(r".\红楼梦\红楼梦带开头.txt", 'w', encoding='utf-8')
for line in file:
if '卷 第' in line:
juan_name = line.strip() + '.txt'
path = os.path.join(r".\红楼梦\分卷", juan_name)
print(path)
if flag == 0:
juan_file = open(path, 'w', encoding='utf-8')
flag = 1
else:
juan_file.close()
juan_file = open(path, 'w', encoding='utf-8')
continue
# 过滤包含手机电子书等信息的行
if ("手机电子书" in line or
"本章字数:" in line or
"更新时间:" in line or
("手机" in line and "电子书" in line and "本章" in line)):
# 跳过这些行
continue
juan_file.write(line)
juan_file.close()
代码分析:
- 使用
open()读取原文件,逐行处理。 - 当检测到"卷 第"时,创建新的分卷文件。
- 通过条件判断过滤无关信息,保留正文内容。
- 最终得到纯净的分卷文本,存储于指定目录。


1.2 分词与停用词过滤
接下来,读取所有分卷文件,使用 jieba 分词,并加载自定义词典(红楼梦词库)提升分词准确性。同时,利用停用词表过滤无意义词汇,生成每回的分词结果文件。
python
filePaths = []
fileContents = []
for root, dfs, files in os.walk(r".\红楼梦\分卷"):
for name in files:
filePath = os.path.join(root, name)
filePaths.append(filePath)
f = open(filePath, 'r', encoding='utf-8')
fileContent = f.read()
f.close()
fileContents.append(fileContent)
corpos = pd.DataFrame(
{
'filePath': filePaths,
'fileContent': fileContents
}
)
print(corpos)
jieba.load_userdict(r".\红楼梦\红楼梦词库.txt")
stopwords = pd.read_csv(r"红楼梦\StopwordsCN.txt", encoding='utf8', engine='python', index_col=False)
file_to_jieba = open(r".\红楼梦\分词后汇总.txt", 'w', encoding='utf-8')
for index, row in corpos.iterrows():
juan_ci = ''
filePath = row['filePath']
fileContent = row['fileContent']
segs = jieba.cut(fileContent)
for seg in segs:
if seg not in stopwords.stopword.values and len(seg.strip()) > 0:
juan_ci += seg + ' '
file_to_jieba.write(juan_ci + '\n')
file_to_jieba.close()
代码分析:
os.walk()遍历分卷文件夹,读取所有文件内容。jieba.load_userdict()加载领域词典,提升人名、地名等专有名词的分词效果。stopwords为停用词表,用于过滤"的"、"了"等无实际意义的词。- 最终生成的分词文件每行对应一回,词语之间以空格分隔。

二、TF-IDF 关键词提取
2.1 读取分词结果与向量化
读取分词后的文本,使用 TfidfVectorizer 将每回文本转换为 TF-IDF 向量。
python
from sklearn.feature_extraction.text import TfidfVectorizer
import pandas as pd
# 读取文件
inFile = open(r".\红楼梦\分词后汇总.txt", 'r', encoding='utf-8')
corpus = inFile.readlines() # 返回列表,每个元素是一行(已分词的一回内容)
# 创建 TF-IDF 向量器
vectorizer = TfidfVectorizer()
tfidf = vectorizer.fit_transform(corpus) # 计算 TF-IDF 矩阵
wordlist = vectorizer.get_feature_names_out() # 获取所有特征词(推荐使用新版方法)
# 创建 DataFrame,行为词语,列为各回
df = pd.DataFrame(tfidf.T.todense(), index=wordlist)
参数与方法说明:
TfidfVectorizer():初始化 TF-IDF 向量化器,默认使用词频与逆文档频率计算。fit_transform(corpus):对分词后的语料进行拟合与转换,返回稀疏矩阵。get_feature_names_out():获取特征词列表,即所有出现的词汇。todense():将稀疏矩阵转换为密集矩阵,便于 DataFrame 处理。
2.2 关键词提取与排序
遍历每一回,提取 TF-IDF 值最高的前10个词语作为该回的核心关键词。
python
# 对每一回进行关键词排序
for i in range(len(corpus)):
featurelist = df.iloc[:, i].tolist() # 获取第 i 列的 TF-IDF 值列表
resdict = {}
# 构建词语到 TF-IDF 值的字典
for j in range(len(wordlist)):
resdict[wordlist[j]] = featurelist[j]
# 按 TF-IDF 值降序排序
resdict = sorted(resdict.items(), key=lambda x: x[1], reverse=True)
# 输出前10个关键词
print('第{}回的核心关键词: '.format(i + 1), resdict[0:10])
代码分析:
df.iloc[:, i]获取第 i 回所有词语的 TF-IDF 值。- 通过字典构建词语与权重的映射。
sorted(resdict.items(), key=lambda x: x[1], reverse=True)按值降序排序。- 输出每回的前10个关键词,反映该回的核心内容与人物。
