ちょっとNLPに触れる機会ができたのでNLPの100本ノックを始めました。
章が終わるたびに載せていきたいと思います。
目次
第1章
準備運動というタイトルになっていて、内容も結構基本的な文字列の扱いの練習になっていました。
逆順などはreversed()
を使って、あとは文字列をリストと見立ててゴチャゴチャ操作する感じで書いていきました。
途中split()
でのデフォルトで文字単位で区切ってくれると勘違いしていて少し引っ掛かったりしました…
問題04で条件が分岐するindexが不規則だったのが気になったけど、辞書のキーが衝突しないように決めたのかなとも思ったり。
n-gramに関してはデータマイニングの授業でも触ったのである程度知っていたのですが、それでも久々にやると結構忘れているものですね…
n-gramの実装中に気になったこととしては、区切る単位(単語か文字か)によって返すリストの形式が変わってしまうところでした。
単語で区切るとList(List(str))
なのに対して文字で区切るとList(str)
なのは少し気になる…
調べた感じだと他の人もそんな感じだったので「良いかな」と割り切って進めていきました。
集合の問題も結構面白かったです。普段あまりset
を使わないので、set
の演算が練習できたのは勉強になりました。かなり直感的に和集合や差集合などを表せることを知ったので、機会があれば使ってみたいと思います。
問題08、09の暗号文、typoglycemiaは簡潔に実装できた気がします。
今回はreturn
を使わずにyield
を使ってみましたが、for
内で変換した文字をreturn用の文字列(または配列)に連結する処理を入れなくていいので、処理だけがあり明解な書き方だなぁと感じました。
cipherは下のように実装しました。
def cipher(string: str):
for s in string:
if s.islower():
yield chr(219 - ord(s))
else:
yield s
"".join((cipher("hoge is fuga.")))
typoglycemiaは下のような感じになりました。
def typoglycemia(string: str):
for s in string.split(" "):
if len(s) > 4:
yield s[0] + "".join(random.sample(s[1:-1], len(s)-2)) + s[-1]
else:
yield s
" ".join(typoglycemia("Alice, a seven-year-old girl, is feeling..."))