blog.hekt.org

Yahoo! Web APIの形態素解析をPythonで使う

ちょっとYahoo! JAPAN Web API形態素解析サービスが必要になったので、Pythonで使うモジュールを書いてみた。2.x系でElementTreeが入っていれば動くはず。2.5以降なら行けるのかな? 3.x系は試してないのでわかりません。

#! /user/bin/env python
# -*- coding: utf-8 -*-

"""
YwaMa = YahooWebApi Marphological Analysis
parameter: http://developer.yahoo.co.jp/webapi/jlp/ma/v1/parse.html
"""

from xml.etree import ElementTree
import urllib

class YwaMa:
	# リクエスト
	def __init__(self, sentence, results='', response='', filter='', ma_response='',
		ma_filter='', uniq_response='', uniq_filter='', uniq_by_baseform=''):
		params = {
			'appid':			"Yahoo! JapanからもらえるアプリケーションID",
			'sentence':			sentence.encode('utf-8'),
			'results':			results,
			'response':			response,
			'filter':			filter,
			'ma_response':		ma_response,
			'ma_filter':		ma_filter,
			'uniq_response':	uniq_response,
			'uniq_filter':		uniq_filter,
			'uniq_by_baseform':	uniq_by_baseform
			}
		base_url = 'http://jlp.yahooapis.jp/MAService/V1/parse'
		params_str = urllib.urlencode(params)

		f = urllib.urlopen(base_url, params_str)
		tree = ElementTree.parse(f)
		elem = tree.getroot()
		self.word_elements = elem.findall(".//{urn:yahoo:jp:jlp}word")

	def str(self, element='surface', delimiter=' '):
		"""
			>>> str()
			u'庭 に は 二 羽 鶏 が いる'
			>>> str(element='reading')
			u'にわ に は 2 わ にわとり が いる'
			>>> str(delimiter='/')
			u'庭/に/は/二/羽/鶏/が/いる'
			>>> str('pos', '|')
			u'名詞|助詞|助詞|名詞|接尾辞|名詞|助詞|動詞'
		"""
		if self.word_elements[0].getiterator("{urn:yahoo:jp:jlp}" + element):
			s = delimiter.join([e.getiterator("{urn:yahoo:jp:jlp}" + element)[0].text for e in self.word_elements])
		else:
			s = ''

		return s

	def li(self, element='surface'):
		"""
			>>> li()
			[u'庭', u'に', u'は', u'二', u'羽', u'鶏', u'が', u'いる']
			>>> li('reading')
			[u'にわ', u'に', u'は', '2', u'わ', u'にわとり', u'が', u'いる']
		"""
		if self.word_elements[0].getiterator("{urn:yahoo:jp:jlp}" + element):
			l = [e.getiterator("{urn:yahoo:jp:jlp}" + element)[0].text for e in self.word_elements]
		else:
			l = []

		return l

	def dic(self):
		"""
			>>> dic()
			[{'reading': u'にわ', 'pos': u'名詞', 'surface': u'庭'},
			{'reading': u'に', 'pos': u'助詞', 'surface': u'に'},
			{'reading': u'は', 'pos': u'助詞', 'surface': u'は'},
			{'reading': '2', 'pos': u'名詞', 'surface': u'二'},
			{'reading': u'わ', 'pos': u'接尾辞', 'surface': u'羽'},
			{'reading': u'にわとり', 'pos': u'名詞', 'surface': u'鶏'},
			{'reading': u'が', 'pos': u'助詞', 'surface': u'が'},
			{'reading': u'いる', 'pos': u'動詞', 'surface': u'いる'}]
		"""
		dic_list = []

		for i in self.word_elements:
			d = {}

			if i.getiterator("{urn:yahoo:jp:jlp}surface"):
				d['surface'] = i.getiterator("{urn:yahoo:jp:jlp}surface")[0].text
			if i.getiterator("{urn:yahoo:jp:jlp}reading"):
				d['reading'] = i.getiterator("{urn:yahoo:jp:jlp}reading")[0].text
			if i.getiterator("{urn:yahoo:jp:jlp}pos"):
				d['pos'] = i.getiterator("{urn:yahoo:jp:jlp}pos")[0].text
			if i.getiterator("{urn:yahoo:jp:jlp}baseform"):
				d['baseform'] = i.getiterator("{urn:yahoo:jp:jlp}baseform")[0].text
			if i.getiterator("{urn:yahoo:jp:jlp}feature"):
				d['feature'] = i.getiterator("{urn:yahoo:jp:jlp}feature")[0].text

			dic_list.append(d)

		return dic_list

文字列にしたりリストにしたり辞書にしたりして返します。

文章中の名詞だけ抜き出して使うとか:

>>> import YwaMa
>>> ma = YwaMa.YwaMa(u"ホセ・ザ・ポエマー。全部で100行くらいの短いプログラムで、
一時間おきにデータベースに登録した文の中からランダムに一つ選んでツイートするだけ。
ちなみにこのアカウントは名前からもわかるように僕がいろいろ遊ぶためのものですから、
いつまでポエムをつぶやき続けるかはわかりませんし、テキトーに拾い集めただけなので
20パターンくらいしかありません。") #実際には改行したら怒られる
>>> for i in ma.dic()
... 	if i['pos'] == u'名詞':
... 		print i['surface']
...
ホセ
ザ
ポエマー
全部
100
プログラム
一
データベース
登録
文
中
ランダム
一つ
ツイート
アカウント
名前
僕
ため
もの
いつ
ポエム
テキトー
20
パターン

こんな感じ。

なんかちょろちょろ細かく変更したくなったので、最新版をこっちに置いておきますねlab.hekt.org/src/yahooma.py