摘要:開撕文件夾下的程序展示了怎么使用這個版本的。文件行數這句是重點摘要然后,我們知道重點函數是,我們再來看它是怎么工作的。再仔細閱讀一遍,原來寫這個庫的大佬用種不同的方法實現了個函數,請收下我的膝蓋。
作者:LogM
本文原載于 https://segmentfault.com/u/logm/articles ,不允許轉載~
1. 源碼來源TextRank4ZH 源碼:https://github.com/letiantian/TextRank4ZH.git
本文對應的源碼版本:committed on 3 Jul 2018, fb1339620818a0b0c16f5613ebf54153faa41636
TextRank 論文地址:https://www.aclweb.org/anthology/W04-3252
2. 概述letiantian 大佬的這個版本,應該是所有 TextRank 的 Python 版本中被點贊最多的。代碼寫的也非常的簡單易懂。
3. 開撕example 文件夾下的程序展示了怎么使用這個版本的 TextRank。有關鍵詞、關鍵短語、關鍵句抽取三種功能,我們這邊只關注關鍵句的抽取。
應該很容易看懂吧,先實例化 TextRank4Sentence,然后使用 analyze 抽取。
# 文件:example/example1.py # 行數:28 tr4s = TextRank4Sentence() tr4s.analyze(text=text, lower=True, source = "all_filters") # 這句是重點 print() print( "摘要:" ) for item in tr4s.get_key_sentences(num=3): print(item.index, item.weight, item.sentence)
然后,我們知道重點函數是 analyze,我們再來看它是怎么工作的。
# 文件:textrank4zh/TextRank4Sentence.py # 行數:43 def analyze(self, text, lower = False, source = "no_stop_words", sim_func = util.get_similarity, pagerank_config = {"alpha": 0.85,}): """ Keyword arguments: text -- 文本內容,字符串。 lower -- 是否將文本轉換為小寫。默認為False。 source -- 選擇使用words_no_filter, words_no_stop_words, words_all_filters中的哪一個來生成句子之間的相似度。 默認值為`"all_filters"`,可選值為`"no_filter", "no_stop_words", "all_filters"`。 sim_func -- 指定計算句子相似度的函數。 """ self.key_sentences = [] result = self.seg.segment(text=text, lower=lower) self.sentences = result.sentences self.words_no_filter = result.words_no_filter self.words_no_stop_words = result.words_no_stop_words self.words_all_filters = result.words_all_filters options = ["no_filter", "no_stop_words", "all_filters"] if source in options: _source = result["words_"+source] else: _source = result["words_no_stop_words"] # 這句是重點 self.key_sentences = util.sort_sentences( sentences = self.sentences, words = _source, sim_func = sim_func, pagerank_config = pagerank_config)
很容易發現,我們需要的內容在 util.sort_sentences 這個函數里。
# 文件:textrank4zh/util.py # 行數:169 def sort_sentences(sentences, words, sim_func = get_similarity, pagerank_config = {"alpha": 0.85,}): """將句子按照關鍵程度從大到小排序 Keyword arguments: sentences -- 列表,元素是句子 words -- 二維列表,子列表和sentences中的句子對應,子列表由單詞組成 sim_func -- 計算兩個句子的相似性,參數是兩個由單詞組成的列表 pagerank_config -- pagerank的設置 """ sorted_sentences = [] _source = words sentences_num = len(_source) graph = np.zeros((sentences_num, sentences_num)) for x in xrange(sentences_num): for y in xrange(x, sentences_num): similarity = sim_func( _source[x], _source[y] ) # 重點1 graph[x, y] = similarity graph[y, x] = similarity nx_graph = nx.from_numpy_matrix(graph) scores = nx.pagerank(nx_graph, **pagerank_config) # 重點2 sorted_scores = sorted(scores.items(), key = lambda item: item[1], reverse=True) for index, score in sorted_scores: item = AttrDict(index=index, sentence=sentences[index], weight=score) sorted_sentences.append(item) return sorted_sentences
這邊有兩個重點,重點1:句子與句子的相似度是如何計算的;重點2:pagerank的實現。
很明顯,PageRank 的實現是借助了 networkx 這個第三方庫,在下一節我們會來看看這個第三方庫的源碼。
這邊,我們先來看重點1,句子與句子的相似度是如何計算的,容易看出,計算方式和論文給的公式是一致的。
# 文件:textrank4zh/util.py # 行數:102 def get_similarity(word_list1, word_list2): """默認的用于計算兩個句子相似度的函數。 Keyword arguments: word_list1, word_list2 -- 分別代表兩個句子,都是由單詞組成的列表 """ words = list(set(word_list1 + word_list2)) vector1 = [float(word_list1.count(word)) for word in words] vector2 = [float(word_list2.count(word)) for word in words] vector3 = [vector1[x]*vector2[x] for x in xrange(len(vector1))] vector4 = [1 for num in vector3 if num > 0.] co_occur_num = sum(vector4) if abs(co_occur_num) <= 1e-12: return 0. denominator = math.log(float(len(word_list1))) + math.log(float(len(word_list2))) # 分母 if abs(denominator) < 1e-12: return 0. return co_occur_num / denominator4. networkx 是怎么實現 PageRank的
不得不說,寫 Python 的好處就是有各種第三方庫可以用。整個PageRank的計算過程,大佬都借助了 networkx 這個第三方庫。
networkx 中 PageRank 的路徑為 networkx/algorithms/link_analysis/pagerank_alg.py。我這邊就不貼出源碼了,共476行,把我驚出一身冷汗。定睛一看,原來注釋占了一半的行數。再仔細閱讀一遍,原來寫這個庫的大佬用3種不同的方法實現了3個 PageRank 函數,請收下我的膝蓋。
Python 的變量類型不明確,比如代碼中 W 這個變量,我知道是一張圖,但我不知道是用鄰接矩陣還是鄰接表或者是自定義類來表示的,需要向上回溯幾層代碼才能知道。所以閱讀這種大工程的 Python 代碼是需要花一點時間的。
如果有耐心理解源碼的話,可以發現,networkx 中 PageRank 和論文中的數學公式還是有些不一樣的,主要的不一樣的點在于對 dangling_nodes 的處理。
5. 總結寫 Python 的好處就是有各種第三方庫可以用。
Python 的變量類型不明確,閱讀大工程的 Python 代碼是需要花一點時間的。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/45181.html
摘要:大家好,我是一行今天給大家聊聊一行在讀研里最成功的投資,那必然是鍵盤邊上的每一本技術書啦畢竟股票基金這種投資即使賺了錢,過段時間就得還回去,非常的神奇但是讀過的每一本技術書籍,都內化在手指上了,只要給個鍵盤,就能給它實 ...
摘要:在函數中通過賦予變量,在函數中,指向定時器以及回調函數當不需要或者時,定時器沒有被,定時器的回調函數以及內部依賴的變量都不能被回收,造成內存泄漏。比如使用了定時器,需要在中做對應銷毀處理。 前言: 3月5日,從中山去往廣州,一大早7點多就做好準備了,在高鐵站了30分鐘,轉廣州地鐵又站了90分鐘,去到地鐵口,就有一輛cvte的大巴車過來接送,我選擇的面試時間是11:00-12:00,但前...
摘要:在函數中通過賦予變量,在函數中,指向定時器以及回調函數當不需要或者時,定時器沒有被,定時器的回調函數以及內部依賴的變量都不能被回收,造成內存泄漏。比如使用了定時器,需要在中做對應銷毀處理。 前言: 3月5日,從中山去往廣州,一大早7點多就做好準備了,在高鐵站了30分鐘,轉廣州地鐵又站了90分鐘,去到地鐵口,就有一輛cvte的大巴車過來接送,我選擇的面試時間是11:00-12:00,但前...
摘要:春招前端實習面試記錄從就開始漸漸的進行復習,月末開始面試,到現在四月中旬基本宣告結束。上海愛樂奇一面盒模型除之外的面向對象語言繼承因為是視頻面試,只記得這么多,只感覺考察的面很廣,前端后端移動端都問了,某方面也有深度。 春招前端實習面試記錄(2019.3 ~ 2019.5) 從2019.1就開始漸漸的進行復習,2月末開始面試,到現在四月中旬基本宣告結束。在3月和4月經歷了無數次失敗,沮...
摘要:面試題答案領取方式見主頁的缺省端口是多少,怎么修改有哪幾種運行模式優化有幾種部署方式容器是如何創建類實例用到了什么原理如何優化內存怎樣調優垃圾回收怎樣策略調優怎樣共享處理怎樣添加遠程監控專業點的分析工具有哪些關于的數目怎樣監視的內存使用情況 TomcatshowImg(https://segmentfault.com/img/remote/1460000019788819);(面試題+...
閱讀 2308·2021-11-24 09:39
閱讀 3038·2021-10-15 09:39
閱讀 3088·2021-07-26 23:38
閱讀 2288·2019-08-30 11:14
閱讀 3409·2019-08-29 16:39
閱讀 1713·2019-08-29 15:23
閱讀 778·2019-08-29 13:01
閱讀 2663·2019-08-29 12:29