Cucco’s Compute Hack

コンピュータ関係の記事を書いていきます。

シーケンシャルなデータに対して、固定のウィンドウ幅での演算を支援する関数

シーケンシャルなデータに対して、固定のウィンドウ幅での演算を支援する関数。mymap()。
指定されたウィンドウ幅でスライスして実際の演算関数に渡す。

シーケンシャルなデータは、1つまたは2つ。将来は可変長引数にしてもよいかもしれない。

コード

def mymap(function_name, window_size, list1, list2=None):
    len_ret =len(list1)
    ret = [None]*len_ret

    assert window_size > 0,"window_size > 0"
    assert type(window_size) is int , "window_size type must be int"

    if list2 is not None:
        assert len_ret == len(list2)

    if list2 is None:
        for i in range(window_size-1, len_ret):#長さ5の時、iの最大は4まで。
            # iはretの添え字
            tmp_list1=list1[i-window_size+1:i+1] #スライスの時、末尾:xのlist1[x]の値は含まれない。
            ret[i]=function_name(tmp_list1)
    else:
        for i in range(window_size-1, len_ret):
            tmp_list1=list1[i-window_size+1:i+1]
            tmp_list2=list2[i-window_size+1:i+1] 
            ret[i]=function_name(tmp_list1,tmp_list2)
    return ret
    
def myaverage(list1):
    return sum(list1)/len(list1)

def myadd(list1):
    return sum(list1)

def mymultadd(list1,list2):
    m=0
    for i in range(len(list1)):
        #print(list1[i] , "*",list2[i])
        m= m + list1[i] * list2[i]
    return m

def myEuclid(list1,list2):
    m=0
    for i in range(len(list1)):
        m = m + (list1[i] - list2[i])**2
    return m

if __name__ == '__main__':

    list1=[1,2,3,4,5]
    list2=[0,0,0,0,0]

    ret = mymap(myadd,1,list1)
    print(ret)
    ret = mymap(myadd,2,list1)
    print(ret)
    ret = mymap(myadd,3,list1)
    print(ret)
    ret = mymap(myadd,4,list1)
    print(ret)
    ret = mymap(myadd,5,list1)
    print(ret)

    ret = mymap(mymultadd,3,list1,list2)
    print(ret)

    ret = mymap(myEuclid,1,list1,list2)
    print(ret)

実行結果

[1, 2, 3, 4, 5]
[None, 3, 5, 7, 9]
[None, None, 6, 9, 12]
[None, None, None, 10, 14]
[None, None, None, None, 15]
[None, None, 0, 0, 0]
[1, 4, 9, 16, 25]