首页 >> 大全

四、实现(TfidfVectorizer计算TF-IDF)

2023-10-10 大全 24 作者:考证青年

文章目录 四、实现(计算TF-IDF) 五、知识点查漏补缺

一、数据集和资料

数据集,提取码:me46

参考博客1:参考博客1

参考博客2:参考博客2

二、流程 从电子邮箱中收集垃圾和非垃圾邮件训练集。读取全部训练集,删除其中的干扰字符,如例如【】*。、,等等,然后分词,删除长度为1的单个字。统计全部训练集中词语的出现次数,截取出现最多的前N个(可以根据实际情况进行调整)根据每个经过第二步预处理后垃圾邮件和非垃圾邮件内容生成特征向量,统计第三步中得到的N个词语在本邮件中出现的频率。根据第四步中得到的特征向量和已知邮件分类创建并训练朴素叶贝斯模型。读取测试邮件,参考第二步,对邮件文本进行预处理,提取特征向量。使用第五步中训练好的模型,根据第六步提取的特征向量对邮件进行分类。 三、实现(自己计算词频) 导包

# -*- coding: utf-8 -*from os import listdir
from re import sub # 字符串正则过滤
from collections import Counter # 单词计数
import numpy as np
import warnings
from jieba import cut # 切词
from sklearn.naive_bayes import MultinomialNB  # 多项式朴素叶贝斯模型
from sklearn.metrics import accuracy_score # 测试

切词

def getWordsFromFile(file_path):"""对文本进行切词:param file_path: txt文本路径:return: 用空格分词的字符串"""words = []with open(file_path, encoding='utf-8') as fp:for line in fp:line = line.strip()# 过滤干扰字符或者无效字符line = sub(r'[.【】0-9、一。,!~\*]', '', line)# 使用jieb的cut函数进行分词line = cut(line)# 过滤长度为1的词line = filter(lambda word: len(word) > 1, line)words.extend(line)return words

读取数据集

def getWords(file_dir):"""将路径下的所有文件加载:param file_dir: 保存txt文件目录:return: 分词后的文档列表"""words=[]file_list = listdir(file_dir)for file in file_list:file_path = file_dir + '/' + filewords.append(getWordsFromFile(file_path))return words

统计训练集中出现最多的TopN个单词

def getTopNWords(words,topN):"""获取出现次数最多的前topN个单词:param words: 需要统计的序列:param topN: 统计的个数:return: 出现次数最多的前topN个单词"""# 因为需要对所有的文本中的单词计数,需要将allWords中的元素(子列表)合并,这里使用了列表推导式实现freq = Counter([x for l in words for x in l])# freq.most_common(topN) 返回  [('blue', 3), ('red', 2)] 我们取每个元素的第一个元素即可return [w[0] for w in freq.most_common(topN)]

生成特征向量

def get_feature(words,topWords):# 获取训练集的特征向量,前600个单词中每个单词在每个邮件中出现的频率"""获取特征向量:param words: 需要获取特征向量的序列:param topWords: topN个单词:return: 特征向量"""features = []for words in words:temp = list(map(lambda x: words.count(x), topWords))features.append(temp)features = np.array(features)return features

函数调用和模型学习

计算实现目标利润的销售量_计算实现的净利润_

# 获取训练数据 topN个单词和特征向量
train_words_list=getWords('data/train')
topWords = getTopNWords(train_words_list,800)
train_features=get_feature(train_words_list, topWords)
# 获取测试数据 和特征向量
test_words_list=getWords('data/test')
test_features=get_feature(test_words_list, topWords)# 邮箱标签,1表示垃圾邮件,0表示正常邮件
train_labels = np.array([1]*127+[0]*24)
test_labels = np.array([1,1,1,1,1,0,0])# 创建叶贝斯模型 ,使用已有数据进行训练
clf = MultinomialNB(fit_prior=False,alpha=0.01).fit(train_features, train_labels)
predicted_labels=clf.predict(test_features)
# 计算准确率
print('训练集精度:',clf.score(train_features, train_labels))
# 测试准确率
print('预测准确率为:', accuracy_score(test_labels, predicted_labels))

完整代码

# -*- coding: utf-8 -*from os import listdir
from re import sub # 字符串正则过滤
from collections import Counter # 单词计数
import numpy as np
import warnings
from jieba import cut # 切词
from sklearn.naive_bayes import MultinomialNB  # 多项式朴素叶贝斯模型
from sklearn.metrics import accuracy_score # 测试warnings.filterwarnings('ignore')def getWordsFromFile(file_path):"""对文本进行切词:param file_path: txt文本路径:return: 用空格分词的字符串"""words = []with open(file_path, encoding='utf-8') as fp:for line in fp:line = line.strip()# 过滤干扰字符或者无效字符line = sub(r'[.【】0-9、一。,!~\*]', '', line)# 使用jieb的cut函数进行分词line = cut(line)# 过滤长度为1的词line = filter(lambda word: len(word) > 1, line)words.extend(line)return wordsdef getWords(file_dir):"""将路径下的所有文件加载:param file_dir: 保存txt文件目录:return: 分词后的文档列表"""words=[]file_list = listdir(file_dir)for file in file_list:file_path = file_dir + '/' + filewords.append(getWordsFromFile(file_path))return words
def getTopNWords(words,topN):"""获取出现次数最多的前topN个单词:param words: 需要统计的序列:param topN: 统计的个数:return: 出现次数最多的前topN个单词"""# 因为需要对所有的文本中的单词计数,需要将allWords中的元素(子列表)合并,这里使用了列表推导式实现freq = Counter([x for l in words for x in l])# freq.most_common(topN) 返回  [('blue', 3), ('red', 2)] 我们取每个元素的第一个元素即可return [w[0] for w in freq.most_common(topN)]
def get_feature(words,topWords):# 获取训练集的特征向量,前600个单词中每个单词在每个邮件中出现的频率"""获取特征向量:param words: 需要获取特征向量的序列:param topWords: topN个单词:return: 特征向量"""features = []for words in words:temp = list(map(lambda x: words.count(x), topWords))features.append(temp)features = np.array(features)return features# 获取训练数据 topN个单词和特征向量
train_words_list=getWords('data/train')
topWords = getTopNWords(train_words_list,800)
train_features=get_feature(train_words_list, topWords)
# 获取测试数据 和特征向量
test_words_list=getWords('data/test')
test_features=get_feature(test_words_list, topWords)# 邮箱标签,1表示垃圾邮件,0表示正常邮件
train_labels = np.array([1]*127+[0]*24)
test_labels = np.array([1,1,1,1,1,0,0])# 创建叶贝斯模型 ,使用已有数据进行训练
clf = MultinomialNB(fit_prior=False,alpha=0.01).fit(train_features, train_labels)
predicted_labels=clf.predict(test_features)
# 计算准确率
print('训练集精度:',clf.score(train_features, train_labels))
# 测试准确率
print('预测准确率为:', accuracy_score(test_labels, predicted_labels))

四、实现(计算TF-IDF) 导包

# -*- coding: utf-8 -*from os import listdir
import numpy as np
import warnings
from jieba import cut  # 切词
from sklearn.feature_extraction.text import TfidfVectorizer  # 计算单词 TF-IDF 向量的值。
from sklearn.naive_bayes import MultinomialNB  # 多项式朴素叶贝斯模型
from sklearn.metrics import accuracy_score  # 测试

切词

def cut_words(file_path):"""对文本进行切词:param file_path: txt文本路径:return: 用空格分词的字符串"""text_with_spaces = ''text = open(file_path, 'r', encoding='UTF-8-sig').read()textcut = cut(text)# 过滤长度为1的词textcut = filter(lambda word: len(word) > 1, textcut)for word in textcut:text_with_spaces += word + ' 'return text_with_spaces

读入数据集

def getWordsFromFile(file_dir):"""将路径下的所有文件加载:param file_dir: 保存txt文件目录:return: 分词后的文档列表"""file_list = listdir(file_dir)words_list = []for file in file_list:file_path = file_dir + '/' + filewords_list.append(cut_words(file_path))return words_list
train_words_list = getWordsFromFile('data/train')
test_words_list = getWordsFromFile('data/test')
# 邮箱标签,1表示垃圾邮件,0表示正常邮件
train_labels = np.array([1]*127+[0]*24)
test_labels = np.array([1, 1, 1, 1, 1, 0, 0])# 读入停止词
stop_words = open('data/stop/stopword.txt', 'r', encoding='UTF-8-sig').read()
stop_words = stop_words.split('\n')  # 根据分隔符分隔

计算TF-IDF 生成特征向量

# 计算单词权重
tf = TfidfVectorizer(stop_words=stop_words, max_df=0.5)train_features = tf.fit_transform(train_words_list)
# 上面fit过了,这里transform
test_features = tf.transform(test_words_list)

模型学习和结果预测

# 多项式贝叶斯分类器
clf = MultinomialNB(fit_prior=False, alpha=0.01).fit(train_features, train_labels)
predicted_labels = clf.predict(test_features)# 计算准确率
print('训练集精度:', clf.score(train_features, train_labels))
# 测试准确率
print('预测准确率为:', accuracy_score(test_labels, predicted_labels))

完整代码

# -*- coding: utf-8 -*from os import listdir
import numpy as np
import warnings
from jieba import cut  # 切词
from sklearn.feature_extraction.text import TfidfVectorizer  # 计算单词 TF-IDF 向量的值。
from sklearn.naive_bayes import MultinomialNB  # 多项式朴素叶贝斯模型
from sklearn.metrics import accuracy_score  # 测试warnings.filterwarnings('ignore')def cut_words(file_path):"""对文本进行切词:param file_path: txt文本路径:return: 用空格分词的字符串"""text_with_spaces = ''text = open(file_path, 'r', encoding='UTF-8-sig').read()textcut = cut(text)# 过滤长度为1的词textcut = filter(lambda word: len(word) > 1, textcut)for word in textcut:text_with_spaces += word + ' 'return text_with_spacesdef getWordsFromFile(file_dir):"""将路径下的所有文件加载:param file_dir: 保存txt文件目录:return: 分词后的文档列表"""file_list = listdir(file_dir)words_list = []for file in file_list:file_path = file_dir + '/' + filewords_list.append(cut_words(file_path))return words_listtrain_words_list = getWordsFromFile('data/train')
test_words_list = getWordsFromFile('data/test')
# 邮箱标签,1表示垃圾邮件,0表示正常邮件
train_labels = np.array([1]*127+[0]*24)
test_labels = np.array([1, 1, 1, 1, 1, 0, 0])# 读入停止词
stop_words = open('data/stop/stopword.txt', 'r', encoding='UTF-8-sig').read()
stop_words = stop_words.split('\n')  # 根据分隔符分隔# 计算单词权重
tf = TfidfVectorizer(stop_words=stop_words, max_df=0.5)train_features = tf.fit_transform(train_words_list)
# 上面fit过了,这里transform
test_features = tf.transform(test_words_list)
# 多项式贝叶斯分类器
clf = MultinomialNB(fit_prior=False, alpha=0.01).fit(train_features, train_labels)
predicted_labels = clf.predict(test_features)# 计算准确率
print('训练集精度:', clf.score(train_features, train_labels))
# 测试准确率
print('预测准确率为:', accuracy_score(test_labels, predicted_labels))

五、知识点查漏补缺 re.sub函数

list.和list.的区别

list.() 向列表中添加一个对象

list.() 把一个序列seq的内容添加到列表中

示例:

music_media = ['compact disc', '8-track tape', 'long playing record']
new_media = ['DVD Audio disc', 'Super Audio CD']
music_media.append(new_media)
>>>['compact disc', '8-track tape', 'long playing record', ['DVD Audio disc', 'Super Audio CD']]music_media.extend(new_media)
>>>['compact disc', '8-track tape', 'long playing record', 'DVD Audio disc', 'Super Audio CD']

.类

是包提供的字典计数器

简单例子:

#统计词频 手写版
colors = ['red', 'blue', 'red', 'green', 'blue', 'blue']
result = {}
for color in colors:if result.get(color)==None:result[color]=1else:result[color]+=1
print(result)
#{'red': 2, 'blue': 3, 'green': 1}# 统计词频 Counter版本
from collections import Counter
colors = ['red', 'blue', 'red', 'green', 'blue', 'blue']
c=Counter(colors)
print(dict(c))
print(c.most_common(2))

numpy.(a, b) 函数

数组以a行b列的数组形式显示

小技巧:

np.arange(16).reshape(2,8) #生成16个自然数,以2行8列的形式显示
# Out: 
# array([[ 0,  1,  2,  3,  4,  5,  6,  7],
#       [ 8,  9, 10, 11, 12, 13, 14, 15]])arr.shape    # (a,b)
arr.reshape(m,-1) #改变维度为m行、d列 (-1表示列数自动计算,d= a*b /m )
arr.reshape(-1,m) #改变维度为d行、m列 (-1表示行数自动计算,d= a*b /m )

关于我们

最火推荐

小编推荐

联系我们


版权声明:本站内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 88@qq.com 举报,一经查实,本站将立刻删除。备案号:桂ICP备2021009421号
Powered By Z-BlogPHP.
复制成功
微信号:
我知道了