1. 程式人生 > >Python中文分詞 jieba

Python中文分詞 jieba

問題 turn Coding windows 停用 分享圖片 詞典 ces text1

三種分詞模式與一個參數

以下代碼主要來自於jieba的github,你可以在github下載該源碼

import jieba

seg_list = jieba.cut("我來到北京清華大學", cut_all=True, HMM=False)  #jieba.cut返回的是一個生成器,而用jieba.lcut會直接返回list
print("Full Mode: " + "/ ".join(seg_list))  # 全模式

seg_list = jieba.cut("我來到北京清華大學", cut_all=False, HMM=True)
print("Default Mode: " + "
/ ".join(seg_list)) # 默認模式 seg_list = jieba.cut("他來到了網易杭研大廈", HMM=False) print(", ".join(seg_list)) seg_list = jieba.cut_for_search("小明碩士畢業於中國科學院計算所,後在日本京都大學深造", HMM=False) # 搜索引擎模式 print(", ".join(seg_list)) # jieba.cut的默認參數只有三個,jieba源碼如下 # cut(self, sentence, cut_all=False, HMM=True) # 分別為:輸入文本 是否為全模式分詞 與是否開啟HMM進行中文分詞

技術分享圖片

關鍵詞提取

from os import path
import jieba.analyse as analyse

d = path.dirname(__file__)

text_path = txt/lz.txt #設置要分析的文本路徑
text = open(path.join(d, text_path)).read()

for key in analyse.extract_tags(text,50, withWeight=False):
# 使用jieba.analyse.extract_tags()參數提取關鍵字,默認參數為50
    print key.encode(
utf-8) # 設置輸出編碼為utf-8不然在因為win下控制臺默認中文字符集為gbk,所以會出現亂碼 # 當withWeight=True時,將會返回number類型的一個權重值(TF-IDF)

技術分享圖片

運行結果如圖所示,但是同樣的我們也發現了一些問題,比如:
問題一:
分詞錯誤,在運行結果中中”路明非”(龍族男主)被分成了”路明”和”明非”啷個中文詞語,這是因為jieba的詞庫中並不含有該詞的原因,同樣的原因以及jieba詞庫比較老,因而在許多文本分詞時都會產生這種情況,而這個問題我們將在第五個模塊”三種可以讓分詞更準確的方法”解決
問題二:
出現非實意詞語,無論在哪種語言中,都會存在大量的非實意單詞,這一類詞雲我們需要在進行中文分詞時進行去除停用詞,這個問題將在下一個模塊中解決

中文歧義測試與去除停用詞

本段代碼主要來自於《機器學習實踐指南(第二版))》,其作者為麥好,ps:這是一本好書

import jieba
TestStr = "2010年底部隊友誼籃球賽結束"
# 因為在漢語中沒有空格進行詞語的分隔,所以經常會出現中文歧義,比如年底-底部-部隊-隊友
# jieba 默認啟用了HMM(隱馬爾科夫模型)進行中文分詞,實際效果不錯

seg_list = jieba.cut(TestStr, cut_all=True)
print "Full Mode:", "/ ".join(seg_list) # 全模式

seg_list = jieba.cut(TestStr, cut_all=False)
print "Default Mode:", "/ ".join(seg_list) # 默認模式
# 在默認模式下有對中文歧義有較好的分類方式

seg_list = jieba.cut_for_search(TestStr) # 搜索引擎模式
print "cut for Search","/".join(seg_list)

技術分享圖片

去除文本中的停用詞

import sys
import jieba
from os import path

d = path.dirname(__file__)
stopwords_path = stopwords\stopwords1893.txt # 停用詞詞表

text_path = txt/lz.txt #設置要分析的文本路徑
text = open(path.join(d, text_path)).read()

def jiebaclearText(text):
    mywordlist = []
    seg_list = jieba.cut(text, cut_all=False)
    liststr="/ ".join(seg_list)
    f_stop = open(stopwords_path)
    try:
        f_stop_text = f_stop.read( )
        f_stop_text=unicode(f_stop_text,utf-8)
    finally:
        f_stop.close( )
    f_stop_seg_list=f_stop_text.split(\n)
    for myword in liststr.split(/):
        if not(myword.strip() in f_stop_seg_list) and len(myword.strip())>1:
            mywordlist.append(myword)
    return ‘‘.join(mywordlist)

text1 = jiebaclearText(text)
print text1

技術分享圖片

三種可以讓分詞更準確的方法

方案一,在jieba中添加中文詞語:
這種方法可以有效的解決之前龍族男主”路明非”被分為”路明”和”明非”兩個詞的情況

#這個只需要在源代碼中加入一個語句即可
import sys
import jieba
from os import path

d = path.dirname(__file__)
stopwords_path = stopwords\stopwords1893.txt # 停用詞詞表

jieba.add_word(路明非)
# 添加的自定義中文語句的代碼在這裏
# 添加的自定義中文語句的代碼在這裏
# 添加的自定義中文語句的代碼在這裏

text_path = txt/lz.txt #設置要分析的文本路徑
text = open(path.join(d, text_path)).read()

def jiebaclearText(text):
    mywordlist = []
    seg_list = jieba.cut(text, cut_all=False)
    liststr="/ ".join(seg_list)
    f_stop = open(stopwords_path)
    try:
        f_stop_text = f_stop.read( )
        f_stop_text=unicode(f_stop_text,utf-8)
    finally:
        f_stop.close( )
    f_stop_seg_list=f_stop_text.split(\n)
    for myword in liststr.split(/):
        if not(myword.strip() in f_stop_seg_list) and len(myword.strip())>1:
            mywordlist.append(myword)
    return ‘‘.join(mywordlist)

text1 = jiebaclearText(text)
print text1

技術分享圖片

方案二,添加自定義詞庫:
下面的代碼主要來自於jieba的github源碼,你可以在github下載該例子

#encoding=utf-8
from __future__ import print_function, unicode_literals
import sys
sys.path.append("../")
import jieba
jieba.load_userdict("userdict.txt")
# jieba采用延遲加載,"import jieba"不會立即觸發詞典的加載,一旦有必要才開始加載詞典構建trie。如果你想手工初始jieba,也可以手動初始化。示例如下:
# import jieba
# jieba.initialize() #手動初始化(可選)
# 在0.28之前的版本是不能指定主詞典的路徑的,有了延遲加載機制後,你可以改變主詞典的路徑:
# 註意用戶詞典為主詞典即優先考慮的詞典,原詞典此時變為非主詞典
# jieba.set_dictionary(‘data/dict.txt.big‘)

import jieba.posseg as pseg

test_sent = (
"李小福是創新辦主任也是雲計算方面的專家; 什麽是八一雙鹿\n"
"例如我輸入一個帶“韓玉賞鑒”的標題,在自定義詞庫中也增加了此詞為N類\n"
"「臺中」正確應該不會被切開。mac上可分出「石墨烯」;此時又可以分出來凱特琳了。"
)
words = jieba.cut(test_sent)
print(/.join(words))

print("="*40)

result = pseg.cut(test_sent)
# pseg.cut 切分,並顯示詞性
# 下面是userdict.txt的內容,如果不加入這個詞庫,那麽在運行結果中,雲計算,創新辦等詞都將無法識別
‘‘‘
雲計算 5
李小福 2 nr
創新辦 3 i
easy_install 3 eng
好用 300
韓玉賞鑒 3 nz
八一雙鹿 3 nz
臺中
凱特琳 nz
Edu Trust認證 2000
‘‘‘

技術分享圖片

下面這段代碼主要來自於jieba的github,你可以在github下載該源碼

print(=*40)
print(添加自定義詞典/調整詞典)
print(-*40)

print(/.join(jieba.cut(如果放到post中將出錯。, HMM=False)))
#如果/放到/post/中將/出錯/。
# 調整詞典使 中將 變為中/將
print(jieba.suggest_freq((, ), True))
#494
print(/.join(jieba.cut(如果放到post中將出錯。, HMM=False)))
#如果/放到/post/中/將/出錯/。
print(/.join(jieba.cut(「臺中」正確應該不會被切開, HMM=False)))
#「/臺/中/」/正確/應該/不會/被/切開
print(jieba.suggest_freq(臺中, True))
print(jieba.suggest_freq(臺中, True))
#69
# 調整詞典使 臺中 不被分詞為臺/中
print(/.join(jieba.cut(「臺中」正確應該不會被切開, HMM=False)))
#「/臺中/」/正確/應該/不會/被/切開

並行計算

下面這段代碼主要來自於jieba的github,你可以在github下載該源碼

原理:將目標文本按行分隔後,把各行文本分配到多個python進程並行分詞,然後歸並結果,從而獲得分詞速度的可觀提升

基於python自帶的multiprocessing模塊,目前暫不支持windows

import sys
import time
sys.path.append("../../")
import jieba

jieba.enable_parallel() # 關閉並行分詞
jieba.enable_parallel(4) # 開啟並行分詞模式,參數為並行進程數 

url = sys.argv[1]
content = open(url,"rb").read()
t1 = time.time()
words = "/ ".join(jieba.cut(content))

t2 = time.time()
tm_cost = t2-t1

log_f = open("1.log","wb")
log_f.write(words.encode(utf-8))

print(speed %s bytes/second % (len(content)/tm_cost))

實驗結果:在4核3.4GHz Linux機器上,對金庸全集進行精確分詞,獲得了1MB/s的速度,是單進程版的3.3倍。

文章轉自:http://blog.csdn.net/fontthrone https://blog.csdn.net/FontThrone/article/details/72782499

Python中文分詞 jieba