diadia

興味があることをやってみる。自分のメモを残しておきます。

データの一般化

プログラミングの基礎を最近読んでいます。OCamlを使ってプログラミングの考え方を学ぶっていうのがこの本のコンセプトです。
https://www.amazon.co.jp/dp/4781911609/

データの一般化

本書120ページあたりから。概要は関数を作っていると似たような関数ができてくる。これらの関数を一般化することでより多くの場面で使うことができるようになる。したがって一般化は大事みたいな内容。

学んだことをpythonで表現

多数決の意見のデータが以下の辞書型データとして存在している。
{"name":"satou", "iken":"yes"}
この辞書型データを格納したリスト型データをopinion_listとする。

opinion_list = [
    {"name":"satou", "iken":"yes"},
    {"name":"yasuda","iken":"no"},
    {"name":"takano","iken":"yes"},
    {"name":"ono",   "iken":"yes"},
]

このリストデータを読み込んで意見が"yes"の人数をカウントするとともに、別の関数として"no"のものも定義してみる。

def count_yes(lst):
    n = 0
    for ele in lst:
        if ele["iken"] == "yes":
            n += 1
        else:
            continue
    print("{}{}{}".format("yes","の人数は",n))
    
    
count_yes(opinion_list)
yesの人数は3

noのものは以下の通り。

def count_no(lst):
    n = 0
    for ele in lst:
        if ele["iken"] == "no":
            n += 1
        else:
            continue
    print("{}{}{}".format("no","の人数は",n))


count_no(opinion_list)
noの人数は1

次に両者を一般化して引数にyes,noを加えることで同じ結果を出力する関数countを設ける。また引数を"yes"として実行結果を確認する。

def count(lst,iken):
    n = 0
    for ele in lst:
        if ele["iken"] == iken:
            n += 1
        else:
            continue
    print("{}{}{}".format(iken,"の人数は",n))



count(opinion_list, "yes")
yesの人数は3

これで引数を変えることでカウントできる関数を作ることができた。しかしながら今までcount_yesをスクリプト上に書いてきた場合、修正が面倒になる。これについても解決できることが判明。それは一般化した関数countを使って再度count_yesを定義しなおすことである。

def count_yes(lst):
    count(lst,"yes")
    
    
count_yes(opinion_list)

結果はもちろん同じになる。

yesの人数は3

一般化した関数を使った場合使わない場合のコードの比較

使わない場合のコード

opinion_list = [
    {"name":"satou", "iken":"yes"},
    {"name":"yasuda","iken":"no"},
    {"name":"takano","iken":"yes"},
    {"name":"ono",   "iken":"yes"},

]

def count_yes(lst):
    n = 0
    for ele in lst:
        if ele["iken"] == "yes":
            n += 1
        else:
            continue
    print("{}{}{}".format("yes","の人数は",n))

    
def count_no(lst):
    n = 0
    for ele in lst:
        if ele["iken"] == "no":
            n += 1
        else:
            continue
    print("{}{}{}".format("no","の人数は",n))

いままでこの書き方をしていた。この書き方しか知らなかった。

一般化した関数を使わう場合のコード

opinion_list = [
    {"name":"satou", "iken":"yes"},
    {"name":"yasuda","iken":"no"},
    {"name":"takano","iken":"yes"},
    {"name":"ono",   "iken":"yes"},

]

def count(lst,iken):
    n = 0
    for ele in lst:
        if ele["iken"] == iken:
            n += 1
        else:
            continue
    print("{}{}{}".format(iken,"の人数は",n))
    

def count_yes(lst):
    count(lst,"yes")
    
def count_no(lst):
    count(lst,"no")

コードをかなりすっきり書くことができた。