【기계 학습】 WordNet을 사용하여 기계적으로 유사한 단어를 추출
자연 언어 처리 개요
WordNet에 대해 언급하기 전에 자연어 처리에 대해 간단히 언급합니다.
자연언어 처리에 있어서 기계가 문장을 이해하게 하기 위해서는 주로 다음과 같이 형태소 해석, 구문 분석, 의미 해석, 문맥 해석의 단계적인 태스크가 필요합니다.
형태소 분석
정보의 주기가 없는 자연 언어의 텍스트 데이터로부터, 대상 언어의 문법이나, 사전이라고 불리는 단어의 품사등의 정보에 근거해, 형태소(언어로 의미를 가지는 최소 단위)의 열로 분할해 판별하는 작업입니다.
예를 들면 「기다리고 있습니다」를 형태소 해석하면 이하와 같이 됩니다.
참고: wikipedia
대표적인 형태소 분석 도구로 MeCab이 있습니다.
구문 분석
자연언어라면 형태소로 나누어, 관계를 도식화하는 등 해 명확하게 하는 수속입니다.
예를 들면 「아름다운 수차 오두막의 처녀」라고 하는 문장이 있었을 때에 이하와 같은 2개의 구문이 생각됩니다.
참고: wikipedia
주위의 형태소의 정보를 바탕으로 어떠한 연결이 있는지를 분석해 갑니다.
대표적인 분석 도구로 Cabocha 등이 있습니다.
의미 분석
기계에 지식을 부여하는 절차입니다. 예를 들어, 다음 문장이 있다고 가정합니다.
"높은 후지산과 바다가 아름답다"
인간이라면 높지만 어떤 단어에 달려 있는지를 곧 알 수 있습니다.
「높은 후지산」은 있어도 「높은 바다」가 없다는 것은 감각적으로 판단할 수 있습니다. 그러나 기계는 아무것도 지식이 없기 때문에 "높은 바다"가 이상하다고 판단 할 수 없습니다.
WordNet이란?
시소러스의 1종. 단어의 상위/하위관계, 부분/전체관계, 동의관계, 동의관계 등에 따라 단어를 분류하여 체계화한 유어사전. 각각의 단어가 어떠한 관계에 있는지를 체계화한 것으로, 상기의 의미 해석 등의 때에 사용됩니다.
예를 들면 「온로드 오토바이」라면, 「온로드 오토바이」를 포함하는 상위 개념이 「오토바이」나 「차량」이며, 하위 개념으로서 「네이키드」 「아메리칸」이라고 하는 오토바이의 종류가 나타납니다. 덧붙여 「오토바이」와 병렬로 기술되고 있는 「스쿠터」 「오프로드 오토바이」등이 유사어로 간주할 수 있습니다.
사용
이것들은 프로그램으로 취급할 수 있도록 정리된 것이 이미 존재하고 있어 이하로부터 다운로드할 수 있습니다. sqlite에서 공개되어 있으며 sql을 사용하여 읽을 수 있습니다.
시소러스의 1종. 단어의 상위/하위관계, 부분/전체관계, 동의관계, 동의관계 등에 따라 단어를 분류하여 체계화한 유어사전. 각각의 단어가 어떠한 관계에 있는지를 체계화한 것으로, 상기의 의미 해석 등의 때에 사용됩니다.
예를 들면 「온로드 오토바이」라면, 「온로드 오토바이」를 포함하는 상위 개념이 「오토바이」나 「차량」이며, 하위 개념으로서 「네이키드」 「아메리칸」이라고 하는 오토바이의 종류가 나타납니다. 덧붙여 「오토바이」와 병렬로 기술되고 있는 「스쿠터」 「오프로드 오토바이」등이 유사어로 간주할 수 있습니다.
사용
이것들은 프로그램으로 취급할 수 있도록 정리된 것이 이미 존재하고 있어 이하로부터 다운로드할 수 있습니다. sqlite에서 공개되어 있으며 sql을 사용하여 읽을 수 있습니다.
pos_def ('pos', lang', def')
link_def ('link', lang','def')
synset_def ('synset', 'lang', 'def', sid')
synset_ex ('synset', 'lang', 'def', 'sid')
synset ('synset', 'pos', 'name', 'src')
synlink ('synset1', synset2', 'link', 'src')
ancestor ('synset1', 'synset2', 'hops')
sense ('synset' ,'wordid','lang', 'rank', 'lexid','freq','src')
word ('wordid','lang', 'lemma', 'pron', 'pos')
variant ('varid','wordid','lang', 'lemma','vartype')
xlink ('synset', 'resource','xref', 'misc', 'confidence')
프로그램
확인 1 : 각 테이블의 열 확인
import sqlite3
conn = sqlite3.connect("wnjpn.db")
def chk_table():
print("")
print("###word table info")
cur = conn.execute("select count(*) from word")
for row in cur:
print("word num:" +str(row[0]))
cur = conn.execute("select name from sqlite_master where type='table'")
for row in cur:
print("=======================================")
print(row[0])
cur = conn.execute("PRAGMA TABLE_INFO("+row[0]+")")
for row in cur:
print(row)
if __name__=="__main__":
chk_table()
###word table info
word num:249121
=======================================
pos_def
(0, 'pos', 'text', 0, None, 0)
(1, 'lang', 'text', 0, None, 0)
(2, 'def', 'text', 0, None, 0)
=======================================
link_def
(0, 'link', 'text', 0, None, 0)
(1, 'lang', 'text', 0, None, 0)
(2, 'def', 'text', 0, None, 0)
=======================================
synset_def
(0, 'synset', 'text', 0, None, 0)
(1, 'lang', 'text', 0, None, 0)
(2, 'def', 'text', 0, None, 0)
(3, 'sid', 'text', 0, None, 0)
=======================================
synset_ex
(0, 'synset', 'text', 0, None, 0)
(1, 'lang', 'text', 0, None, 0)
(2, 'def', 'text', 0, None, 0)
(3, 'sid', 'text', 0, None, 0)
=======================================
synset
(0, 'synset', 'text', 0, None, 0)
(1, 'pos', 'text', 0, None, 0)
(2, 'name', 'text', 0, None, 0)
(3, 'src', 'text', 0, None, 0)
=======================================
synlink
(0, 'synset1', 'text', 0, None, 0)
(1, 'synset2', 'text', 0, None, 0)
(2, 'link', 'text', 0, None, 0)
(3, 'src', 'text', 0, None, 0)
=======================================
ancestor
(0, 'synset1', 'text', 0, None, 0)
(1, 'synset2', 'text', 0, None, 0)
(2, 'hops', 'int', 0, None, 0)
=======================================
sense
(0, 'synset', 'text', 0, None, 0)
(1, 'wordid', 'integer', 0, None, 0)
(2, 'lang', 'text', 0, None, 0)
(3, 'rank', 'text', 0, None, 0)
(4, 'lexid', 'integer', 0, None, 0)
(5, 'freq', 'integer', 0, None, 0)
(6, 'src', 'text', 0, None, 0)
=======================================
word
(0, 'wordid', 'integer', 0, None, 1)
(1, 'lang', 'text', 0, None, 0)
(2, 'lemma', 'text', 0, None, 0)
(3, 'pron', 'text', 0, None, 0)
(4, 'pos', 'text', 0, None, 0)
=======================================
variant
(0, 'varid', 'integer', 0, None, 1)
(1, 'wordid', 'integer', 0, None, 0)
(2, 'lang', 'text', 0, None, 0)
(3, 'lemma', 'text', 0, None, 0)
(4, 'vartype', 'text', 0, None, 0)
=======================================
xlink
(0, 'synset', 'text', 0, None, 0)
(1, 'resource', 'text', 0, None, 0)
(2, 'xref', 'text', 0, None, 0)
(3, 'misc', 'text', 0, None, 0)
(4, 'confidence', 'text', 0, None, 0)
확인2 : 등록된 단어(일본어) 확인
import sqlite3
conn = sqlite3.connect("wnjpn.db")
def chk_word():
#cur = conn.execute("select * from word limit 240000")
cur = conn.execute("select * from word where lang='jpn' limit 240000")
for row in cur:
print(row)
if __name__=="__main__":
chk_word()
일부만 표시
(249100, 'jpn', 'スープ皿', None, 'n')
(249101, 'jpn', '引延す', None, 'v')
(249102, 'jpn', '渋色', None, 'n')
(249103, 'jpn', '断書き', None, 'n')
(249104, 'jpn', 'オールボルグ', None, 'n')
(249105, 'jpn', 'うしろ側', None, 'n')
(249106, 'jpn', '取繕', None, 'n')
(249107, 'jpn', '利便', None, 'n')
(249108, 'jpn', '利便', None, 'a')
(249109, 'jpn', 'ヴァイラス', None, 'n')
(249110, 'jpn', '古めかしい', None, 'a')
(249111, 'jpn', '懇切', None, 'n')
(249112, 'jpn', '懇切', None, 'a')
(249113, 'jpn', '超文面', None, 'n')
(249114, 'jpn', '性病', None, 'n')
(249115, 'jpn', 'まゆ墨', None, 'n')
(249116, 'jpn', 'ヘムライン', None, 'n')
(249117, 'jpn', '非近交系', None, 'a')
(249118, 'jpn', '科学機器', None, 'n')
(249119, 'jpn', '後ずさる', None, 'v')
(249120, 'jpn', '引繰り返す', None, 'v')
(249121, 'jpn', '意志', None, 'n')
확인 3 : 동의어 추출
import sqlite3
conn = sqlite3.connect("wnjpn.db")
def main(word):
print("")
print("")
print("## 入力: 【",word,"】")
print("")
# 単語がWordnetに存在するか確認
cur = conn.execute("select wordid from word where lemma='%s'" % word)
word_id = 99999999
for row in cur:
word_id = row[0]
if word_id==99999999:
print("「%s」is not exist" % word)
return
#概念を取得
cur = conn.execute("select synset from sense where wordid='%s'" % word_id)
synsets = []
for row in cur:
synsets.append(row[0])
print(synsets)
#概念に含まれる単語の表示
for synset in synsets:
cur1 = conn.execute("select name from synset where synset='%s'" % synset)
for row1 in cur1:
print("## 概念: %s" %(row1[0]))
cur2 = conn.execute("select def from synset_def where (synset='%s' and lang='jpn')" % synset)
for row2 in cur2:
print("## 意味: %s" %(row2[0]))
cur3 = conn.execute("select wordid from sense where (synset='%s' and wordid!=%s)" % (synset,word_id))
for i,row3 in enumerate(cur3):
target_word_id = row3[0]
cur3_1 = conn.execute("select lemma from word where wordid=%s" % target_word_id)
for row3_1 in cur3_1:
print("類義語"+str(i+1)+": %s" % (row3_1[0]))
print()
if __name__=="__main__":
word="自動車"
main(word)
## 入力: 【 自動車 】
['03791235-n', '02958343-n']
## 概念: motor_vehicle
## 意味: レールの上を走らない自動推進式の車輪のついた乗物
類義語1: motor_vehicle
類義語2: automotive_vehicle
類義語3: モータービークル
## 概念: auto
## 意味: 4輪の自動車
## 意味: 通常、内燃エンジンによって推進する
類義語1: auto
類義語2: motorcar
類義語3: machine
類義語4: car
類義語5: automobile
類義語6: 四輪車
類義語7: オートモービル
類義語8: 車
類義語9: 乗用車
類義語10: オートモビル
類義語11: モーターカー
유사어 추출의 흐름으로서 「자동차」를 입력하면 우선, 자동차의 상위 개념인 「motor_vehicle」 「auto」를 따라, 그 부하에 있는 단어를 추출하는 것으로, 「자동차」와 병렬 관계에 있는 단어를 꺼내고 있습니다.
Reference
이 문제에 관하여(【기계 학습】 WordNet을 사용하여 기계적으로 유사한 단어를 추출), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/asakbiz/items/f82e95c13e5e9599306c텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)