Word2vec+textrank---抽取式摘要生成

2023-10-13 04:20

本文主要是介绍Word2vec+textrank---抽取式摘要生成,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

原项目地址:
https://github.com/ztz818/Automatic-generation-of-text-summaries

相关知识介绍:
Word2Vec理论知识:https://blog.csdn.net/Pit3369/article/details/96482304
中文文本关键词抽取的三种方法(TF-IDF、TextRank、word2vec):
https://blog.csdn.net/Pit3369/article/details/95594728

调用summarize(text, n)返回Top N个摘要

  1. tokens = cut_sentences(text)

    按照。!?切分句子,返回给tokens[[句子1],[句子2]]

  2. 对句子tokens分词、通用词,返回列表sents:[[句子1分词结果],[句子2分词结果]],分词结果空格隔开

  3. sents = filter_model(sents)

    遍历列表,去除word2vec词向量里未出现的词。

  4. graph = create_graph(sents)

    传入句子列表,返回句子间相似度的图board[n*n],句子个数为n,图元素为i、j句子的相似值
    在这里插入图片描述

    • 循环i、j:board[i][j] = compute_similarity_by_avg(word_sent[i], word_sent[j])

      compute_similarity_by_avg(sents_1, sents_2)中,把句子中各个词词向量相加,除以句子长度作为句子平均得分,用来计算两个句子的相似度,返回给create_graph

    • 用句子i、j的平均词向量进行相似度计算,相似值存储在board[i][j],返回给相似度图矩阵graph[][]

  5. scores = weight_sentences_rank(graph)
    输入相似度图矩阵graph[n*n],返回句子分数数组:scores[i],句子i的分值,初始值为0.5

    while循环迭代直至句子i分数变化稳定在0.0001:

    • scores[i] = calculate_score(weight_graph, scores, i)

      计算句子在图中分数,返回句子i的分数。参数j遍历所有句子:

      • 计算分子:fraction = weight_graph[j][i] * scores[j]
      • 计算分母:denominator += weight_graph[j][k],参数k遍历句子j、k是否关联
      • 分数累加:added_score += fraction / denominator
      • 根据PageRank算法中PR值的计算方法,算出最终的分数,并返回:
        weighted_score = (1 - d) + d * added_score
        在这里插入图片描述
  6. sent_selected = nlargest(n, zip(scores, count()))

    选取句子分数scores[],Top n的句子,作为摘要。

相似值计算:
使用的计算句子相似度的方式如下:

如计算句子A=[‘word’,‘you’,‘me’],与句子B=[‘sentence’,‘google’,‘python’]计算相似性,从word2vec模型中分别得到A中三个单词的词向量v1,v2,v3取其平均值Va(avg)=(v1+v2+v3)/3。对句子B做同样的处理得到Vb(avg),然后计算Va(avg)与Vb(avg)连个向量的夹角余弦值,Cosine Similarity视为句子A与B的相似度
在这里插入图片描述

def cut_sentences(sentence):puns = frozenset(u'。!?')#分隔句子tmp = []for ch in sentence:tmp.append(ch)if puns.__contains__(ch):yield ''.join(tmp)tmp = []yield ''.join(tmp)# 句子中的stopwords
def create_stopwords():stop_list = [line.strip() for line in open("G:\1graduate\news_stopwords.txt", 'r', encoding='utf-8').readlines()]return stop_listdef two_sentences_similarity(sents_1, sents_2):'''计算两个句子的相似性:param sents_1::param sents_2::return:'''counter = 0for sent in sents_1:if sent in sents_2:counter += 1return counter / (math.log(len(sents_1) + len(sents_2)))def create_graph(word_sent):"""传入句子链表  返回句子之间相似度的图:param word_sent::return:"""num = len(word_sent)print("句子数量:",num)board = [[0.0 for _ in range(num)] for _ in range(num)]#num*numprint("board大小:",len(board),len(board[0]))"""词向量平均值作为计算句子i,j相似度的依据,保存到数组product(A,B)函数,返回A和B中的元素组成的笛卡尔积的元组"""for i, j in product(range(num), repeat=2):if i != j:board[i][j] = compute_similarity_by_avg(word_sent[i], word_sent[j])return boarddef cosine_similarity(vec1, vec2):'''计算两个向量之间的余弦相似度:param vec1::param vec2::return:(XY对应元素相乘之和)/((X元素平方和开根号)+(Y元素平方和开根号))'''tx = np.array(vec1)ty = np.array(vec2)cos1 = np.sum(tx * ty)cos21 = np.sqrt(sum(tx ** 2))cos22 = np.sqrt(sum(ty ** 2))cosine_value = cos1 / float(cos21 * cos22)return cosine_valuedef compute_similarity_by_avg(sents_1, sents_2):'''对两个句子求平均词向量:param sents_1::param sents_2::return:'''# print("计算句子相似度:",sents_1, sents_2)if len(sents_1) == 0 or len(sents_2) == 0:return 0.0"""句子中各个词向量相加,再平均,作为相似度计算依据if判断,避免了for循环vec1作为空值的异常"""if sents_1[0] in model:vec1 = model[sents_1[0]]else:vec1=model['中国']for word1 in sents_1[1:]:if word1 in model:vec1 = vec1 + model[word1]else:vec1 = vec1 + model['中国']if sents_2[0] in model:vec2 = model[sents_2[0]]else:vec2=model['中国']for word2 in sents_2[1:]:if word2 in model:        vec2 = vec2 + model[word2]else:vec2 = vec2 + model['中国']# 词向量元素均除以句子长度similarity = cosine_similarity(vec1 / len(sents_1), vec2 / len(sents_2))return similaritydef calculate_score(weight_graph, scores, i):"""计算句子在图中的分数:param weight_graph::param scores::param i::return:"""length = len(weight_graph)d = 0.85added_score = 0.0for j in range(length):fraction = 0.0denominator = 0.0# 计算分子,第j个句子的词语ifraction = weight_graph[j][i] * scores[j]# 计算分母for k in range(length):denominator += weight_graph[j][k]if denominator == 0:denominator = 1added_score += fraction / denominator# 根据PageRank算法中PR值的计算方法,算出最终的分数weighted_score = (1 - d) + d * added_scorereturn weighted_scoredef weight_sentences_rank(weight_graph):'''输入相似度的图(矩阵)返回各个句子的分数:param weight_graph::return:'''# 初始分数设置为0.5scores = [0.5 for _ in range(len(weight_graph))] # 根据句子数量建立的矩阵,存储每个句子的得分old_scores = [0.0 for _ in range(len(weight_graph))]print("scores矩阵:",len(scores))# 开始迭代# 判断前后分数有无变化while different(scores, old_scores):for i in range(len(weight_graph)):old_scores[i] = scores[i]for i in range(len(weight_graph)):# 句子序号i,计算每个句子的词向量得分scores[i] = calculate_score(weight_graph, scores, i)return scoresdef different(scores, old_scores):'''判断前后分数有无变化:param scores::param old_scores::return:'''flag = Falsefor i in range(len(scores)):if math.fabs(scores[i] - old_scores[i]) >= 0.0001:flag = Truebreakreturn flagdef filter_symbols(sents):stopwords = create_stopwords() + ['。', ' ', '.']_sents = []for sentence in sents:for word in sentence:if word in stopwords:sentence.remove(word)if sentence:_sents.append(sentence)return _sentsdef filter_model(sents):_sents = []for sentence in sents:for word in sentence:if word not in model:sentence.remove(word)if sentence:_sents.append(sentence)else:print("移除句子",sentence)return _sentsdef summarize(text, n):#     按照。!?分句tokens = cut_sentences(text)sentences = []sents = []for sent in tokens:sentences.append(sent)sents.append([word for word in jieba.cut(sent) if word])# 按句分词,得到列表套列表,1句子,2按句分词print(len(sents))# print((sents))# sents = filter_symbols(sents)# 移除模型中没有的词sents = filter_model(sents)print("过滤模型后句子数量",len(sents))graph = create_graph(sents)print("词向量图矩阵建立完毕~")print("词向量图矩阵:",len(graph))# 句子个数,每行元素为该句子中词的词向量scores = weight_sentences_rank(graph)sent_selected = nlargest(n, zip(scores, count()))sent_index = []print("sent_selected=",(sent_selected))# 句子分数,句子编号for i in range(n):
#         sent_index.append(sent_selected[i][1])sent_index.append(sent_selected[i][1])return [sentences[i] for i in sent_index]

这篇关于Word2vec+textrank---抽取式摘要生成的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/200738

相关文章

MybatisGenerator文件生成不出对应文件的问题

《MybatisGenerator文件生成不出对应文件的问题》本文介绍了使用MybatisGenerator生成文件时遇到的问题及解决方法,主要步骤包括检查目标表是否存在、是否能连接到数据库、配置生成... 目录MyBATisGenerator 文件生成不出对应文件先在项目结构里引入“targetProje

Python使用qrcode库实现生成二维码的操作指南

《Python使用qrcode库实现生成二维码的操作指南》二维码是一种广泛使用的二维条码,因其高效的数据存储能力和易于扫描的特点,广泛应用于支付、身份验证、营销推广等领域,Pythonqrcode库是... 目录一、安装 python qrcode 库二、基本使用方法1. 生成简单二维码2. 生成带 Log

Python使用Pandas库将Excel数据叠加生成新DataFrame的操作指南

《Python使用Pandas库将Excel数据叠加生成新DataFrame的操作指南》在日常数据处理工作中,我们经常需要将不同Excel文档中的数据整合到一个新的DataFrame中,以便进行进一步... 目录一、准备工作二、读取Excel文件三、数据叠加四、处理重复数据(可选)五、保存新DataFram

SpringBoot生成和操作PDF的代码详解

《SpringBoot生成和操作PDF的代码详解》本文主要介绍了在SpringBoot项目下,通过代码和操作步骤,详细的介绍了如何操作PDF,希望可以帮助到准备通过JAVA操作PDF的你,项目框架用的... 目录本文简介PDF文件简介代码实现PDF操作基于PDF模板生成,并下载完全基于代码生成,并保存合并P

详解Java中如何使用JFreeChart生成甘特图

《详解Java中如何使用JFreeChart生成甘特图》甘特图是一种流行的项目管理工具,用于显示项目的进度和任务分配,在Java开发中,JFreeChart是一个强大的开源图表库,能够生成各种类型的图... 目录引言一、JFreeChart简介二、准备工作三、创建甘特图1. 定义数据集2. 创建甘特图3.

AI一键生成 PPT

AI一键生成 PPT 操作步骤 作为一名打工人,是不是经常需要制作各种PPT来分享我的生活和想法。但是,你们知道,有时候灵感来了,时间却不够用了!😩直到我发现了Kimi AI——一个能够自动生成PPT的神奇助手!🌟 什么是Kimi? 一款月之暗面科技有限公司开发的AI办公工具,帮助用户快速生成高质量的演示文稿。 无论你是职场人士、学生还是教师,Kimi都能够为你的办公文

pdfmake生成pdf的使用

实际项目中有时会有根据填写的表单数据或者其他格式的数据,将数据自动填充到pdf文件中根据固定模板生成pdf文件的需求 文章目录 利用pdfmake生成pdf文件1.下载安装pdfmake第三方包2.封装生成pdf文件的共用配置3.生成pdf文件的文件模板内容4.调用方法生成pdf 利用pdfmake生成pdf文件 1.下载安装pdfmake第三方包 npm i pdfma

poj 1258 Agri-Net(最小生成树模板代码)

感觉用这题来当模板更适合。 题意就是给你邻接矩阵求最小生成树啦。~ prim代码:效率很高。172k...0ms。 #include<stdio.h>#include<algorithm>using namespace std;const int MaxN = 101;const int INF = 0x3f3f3f3f;int g[MaxN][MaxN];int n

poj 1287 Networking(prim or kruscal最小生成树)

题意给你点与点间距离,求最小生成树。 注意点是,两点之间可能有不同的路,输入的时候选择最小的,和之前有道最短路WA的题目类似。 prim代码: #include<stdio.h>const int MaxN = 51;const int INF = 0x3f3f3f3f;int g[MaxN][MaxN];int P;int prim(){bool vis[MaxN];

poj 2349 Arctic Network uva 10369(prim or kruscal最小生成树)

题目很麻烦,因为不熟悉最小生成树的算法调试了好久。 感觉网上的题目解释都没说得很清楚,不适合新手。自己写一个。 题意:给你点的坐标,然后两点间可以有两种方式来通信:第一种是卫星通信,第二种是无线电通信。 卫星通信:任何两个有卫星频道的点间都可以直接建立连接,与点间的距离无关; 无线电通信:两个点之间的距离不能超过D,无线电收发器的功率越大,D越大,越昂贵。 计算无线电收发器D