LoginSignup
1
0

More than 5 years have passed since last update.

クロージャつかってローパスフィルタ

Last updated at Posted at 2017-02-04

はじめに

履歴を残すための変数をグローバルで置くとスコープが広がって嫌だな〜と思ってましたが、クロージャを使えば隠しておけるんですね。自分用のメモです。

コード

import numpy as np

def get_lpf(alpha):
    prev = np.nan * np.ones(1)
    calc = lambda pre, new : alpha * prev + (1.-alpha) * new

    def lpf(val):
        prev[0] = calc(prev[0], val) if not np.isnan(prev[0]) else val
        return prev[0]

    return lpf

lpf = get_lpf(0.8)

for i in range(100):
    new = numpy.random.normal()
    filtered = lpf(new)

    print("new=%f, filt=%f" % (new, filtered) )

解説的なもの

prev = np.nan * np.ones(1)
calc = lambda pre, new : alpha * prev + (1.-alpha) * new
  • 履歴保持用の変数 prev をlpfの生成用関数 get_lpf 内で作る
  • calc はLPFの計算 $y_n = \alpha y_{n-1} + (1-\alpha)x_n$ を実行する関数
prev[0] = calc(prev[0], val) if not np.isnan(prev[0]) else val
  • prev = としてしまうと、外部変数の参照ではなく新たに定義したと認識されてエラーになる
  • 長さ1の配列を定義し、配列の要素を参照するようにすることで、無理やり参照扱いにする
  • prevnumpy.nan で初期化しているので、 numpy.nan でなくなるまではそのまま出力する
1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0