tonkatuのおしゃべり

まっきーの研鑽記

ラーメン二郎には二度と行かねえ

Python 辞書を更新して返す関数を作ったけど

カロリーメイトSOYJOYだけで夜飯を賄うにはどの種類をどれだけ食べれば良いか」という質問をYahoo知恵袋に投げるかで悩んでいる。

というのは置いといて、今回はPythonで辞書を更新して返す関数を作ったけど、もっとエレガントな書き方無いのかな〜というご相談。

追記

解決しました。

stackoverflow.com ここで書かれている z = {**x, **y} という表現が最強ですね。やはりpythonは英語でググるのがベストだなぁ。stack overflowのコミュニティが活発だなという印象。 ここも参考にしました。

複数の辞書のマージ方法いろいろ - Qiita

背景としては、MicrosoftのText Analytics API (英語文章のネガポジ度などを解析するやーつ)を叩くプログラムを書いていて、jsonをPOSTするために辞書型にデータをいい感じに格納したいと思った感じ。

こういうjsonをPOSTしたい。

request = {
    "documents": [
        {"language": "en", "id": 0, "text": "hogehoge"},
        {"language": "en", "id": 1, "text": "fugafuga"},
        ...
        {"language": "en", "id": 99, "text": "piyopiyo"}
    ]
}

上の "language" は全て "en" で、"id" はそれぞれユニークで、"text" に解析する文字列を入れる。今回は解析する文字列はリストで translated_texts に格納されているとする。(名前は気にしないで) この translated_texts リストを使って request 辞書をうま〜く作りたい。

documents_template = {
    "language": "en"
}


def return_updated_dic(dic, added_dic=None, **kwargs):
    new_dic = dic.copy()
    if added_dic:
        for k, v in added_dic.items():
            new_dic.update({k: v})
    else:
        for k, v in kwargs.items():
            new_dic.update({k: v})
    return new_dic

added_dics = map(lambda x, y: {'text': x, 'id': y},
                 translated_texts, itertools.count(1))
documents = map(partial(return_updated_dic, documents_template),
                added_dics)

request = {
  "documents": list(documents)
}
request_str = json_dumps(request)

(partialはfuctoosl.partial)

なんかね。自分でも周りくどいことしてるなと思う。 最終的には request["documents"] にリストをぶちこみたいので、そのリスト documents をどうやって作るか考えたんだけど、最近関数型っぽいプログラミングにはまっているので map 関数を使って作りたかったんです\(^o^)/。 だけど、pythonの辞書型はmutableなのでupdate()が破壊的メソッドであり、mapと相性が悪かった。悪いよね?だから新しく、return_updated_dicなる関数を作ってそれをmapに渡してる感じ。

これで一応望み通りの結果にはなるんだけど、もっとエレガントな書き方ないかな〜??なんか便利なライブラリあるとか?う〜ん。教えて。

普通にfor文を使えば

documents = []
for i, translated_text in enumerate(translated_texts):
    documents.append({"language": "en", "id": i, "text": translated_text})

で済む話なんだけど、、、笑 map使いたいねん。

(最近haskell入門しててそーゆー病気になったのかも)