對一篇文章,一般的做法是先進行分詞,後續是對詞語進行語義特徵提取與建模,不過也有人是用句子或者單字粒度,個人實驗的結果是字元級比分詞好,句子級沒有試過。
分詞後是去除停用詞以及標點符號,停用詞表到github上搜尋一下有挺多,裡面是像咳、哇、哈這些沒啥用的詞,把他們去掉對文字語義沒什麼影響,卻可以降低文字處理的複雜度,詞的個數越少,表示乙個詞或者句子的向量維度就可以更低。
分詞一般使用jieba庫來分詞,這裡也推薦另乙個 synonyms包。他是在jieba的基礎上做的,在一些方面更方便,做一下對比:
總體感覺synonyms分詞、詞性標註一次性完成比較方便,功能也豐富。兩者也可組合使用。
注意兩個包組合使用時,jieba在前,synonyms在後,不然會報錯。
import jieba
import jieba.posseg as pseq
import synonyms
引用synonyms的時候,會發現有這麼一句輸出,可以知道裡面也是有用jieba的來分詞的
分別用jieba、synonyms分詞跟詞性標註,發現結果是一樣的。注意輸入只能是乙個字串,不能輸入多個,多個文字就用迴圈。
# 要分詞的文字
text =
'今天a區陽光明媚!'
# jieba分詞,lcut直接返回分詞列表
result1 = jieba.lcut(text)
print
('jieba分詞結果:'
,result1)
# jieba詞性標註,返回的是乙個迭代器,只能迭代一次
result2 = pseq.cut(text)
print
('jieba詞性標註結果:'
)for word in result2:
# 迭代物件包含詞、詞性兩個屬性
print
(word.word, word.flag)
輸出為
jieba分詞結果: [『今天』, 『a』, 『區』, 『陽光明媚』, 『!』]jieba詞性標註結果:
今天 t
a eng
區 n陽光明媚 nr
! x
text =
'今天a區陽光明媚!'
# synonyms分詞、詞性標註
# 一次性返回兩個列表,第乙個列表是分詞結果,第二個是詞性標註結果
result3 = synonyms.seg(text)
print
('synonyms分詞結果:'
)print
(result3[0]
)print
('synonyms詞性標註結果:'
)print
(result3[1]
)
輸出為
synonyms分詞結果:對比可以發現,兩個的分詞跟詞性標註結果是一樣的。[『今天』, 『a』, 『區』, 『陽光明媚』, 『!』]
synonyms詞性標註結果:
[『t』, 『eng』, 『n』, 『nr』, 『x』]
向 『今天a區陽光明媚!』 這句話的分詞,可以發現有一些詞語是分不出來的,可能是專用詞或者特殊詞之類的,這個時候可以給jieba匯入乙個自定義詞典,他就可以將這些詞成功分出來。synonyms新增詞典也是用jieba新增即可
新增詞典有兩種方式:
# 新增單個詞
jieba.add_word(word=
'a區'
,freq=
5,tag=
'n')
# txt檔案形式新增
# 每一行表示乙個詞:詞 詞頻 詞性
jieba.load_userdict(
'./自定義詞典.txt'
)
新增詞典後的分詞結果
text =
'今天a區陽光明媚!'
# 新增詞典結果對比
result4=synonyms.seg(text)
print
('新增詞典前:'
)print
(result3[0]
,'\n'
)print
('新增詞典後:'
)print
(result4[0]
)
輸出為
新增詞典前:可以發現新增詞典後對新語料分詞準確很多。[『今天』, 『a』, 『區』, 『陽光明媚』, 『!』]
新增詞典後:
[『今天』, 『a區』, 『陽光明媚』, 『!』]
要去除停用詞,首先得有乙個停用詞表,這裡給github上的乙個資源。分詞後,篩選掉當中的停用詞就好了,當然也可以篩選調某些詞性或者標點符號,做法是一樣的。
用這個讀取檔案,成為乙個列表。
stopwords =
[w.strip(
)for w in
open
('停用詞表.txt'
,'r'
, encoding=
'utf-8'
).readlines(
)]
演示的用下面的代替:
stopwords =
['今天'
,'!'
]result_clean =
for word in result4[0]
:if word not
in stopwords:
print
('去除停用詞結果'
, result_clean)
輸出為:
去除停用詞結果 [『a區』, 『陽光明媚』]預處理這裡也有看到有人用近義詞替換,我試著效果不是很好。用的是synonyms.nearby(word)
# 返回乙個元組,包含兩個列表
# 第乙個列表是近義詞
# 第二個列表是對應的相似度
word=
'交叉口'
near=synonyms.nearby(word)
print
('結果型別:'
,type
(near)
)print
('結果長度:'
,len
(near)
)print
('近義詞:'
,near[0]
)print
('相似度:'
,near[1]
)
輸出為
結果型別:結果長度: 2
近義詞: [『交叉口』, 『路口』, 『交叉路口』, 『中山路』, 『街口』, 『交口』, 『和平路』, 『中山北路』, 『交叉處』, 『東南側』]
相似度: [1.0, 0.81871194, 0.7977913, 0.7161459, 0.6995231, 0.69011694, 0.6796811, 0.66988134, 0.6574828, 0.64784586]
line=
'未管所路**叉口至加油站路段'
line=jieba.lcut(line)
line_new=
for word in line:
near_word=synonyms.nearby(word)
for i in
range(1
,len
(near_word[0]
)):if near_word[0]
[i]in line_new and near_word[1]
[i]>
0.8:
word=near_word[0]
[i]break
print
('未替換結果:'
,line)
print
('分詞結果:'
,line_new)
輸出為
未替換結果: [『未管』, 『所』, 『路口』, 『交叉口』, 『至』, 『加油站』, 『路段』]知乎上的乙個分詞介紹,提供了其他的分詞方法,不過沒去試過:分詞結果: [『未管』, 『所』, 『路口』, 『路口』, 『至』, 『加油站』, 『路段』]
github上的乙個nlp專案,收集了很多資源:
NLP 中文文字預處理
jieba是乙個專門處理中文分詞的分詞庫,但其實功能比單純的分詞強大許多。中文不同於英文可以通過空格分開每個有意義的詞,對於中文需要乙個工具將完整的文字分割成更細緻的詞語,類似於英文分詞中使用的nltk工具,中文中需要使用jieba。pip install jieba 4.詞性標註 5.tokeni...
小語種nlp文字預處理 資料清洗
開始繼續完成大資料實驗室招新題 roman urdu小語種為例 link 本練習賽所用資料,是名為 roman urdu dataset 的公開資料集。這些資料,均為文字資料。原始資料的文字,對應三類情感標籤 positive,negative,netural。本練習賽,移除了標籤為netural的...
NLP文字預處理的一些方法
寫在前面 隨著bert等技術的興起,在做文字方面比賽時,對於預處理這一塊像中文分詞,停用詞過濾,詞形還原,詞幹化,標點符號處理等變的不再這麼重要。當然也可以從另乙個角度來看,這些對於文字的預處理方法相當於減少輸入的雜訊,是可以讓神經網路更具有魯棒性的。所以以下內容可以作為乙個知識儲備在這裡,在工作中...