Data.Vector型をリストのようにパターンマッチできないかなと調べていた時に、2ちゃんねるのプログラム技術板に以下のようなコメントを目にした。
このヒントに基づいて、以下のように、データ列をData.Vector.UnboxedとしたIIRフィルタを実装してみた。が、Cで書いたものよりも、2000倍!ほど遅い。ただならぬ遅さである。データ列をData.Array.Unboxedにして実装してみたら、Cの約3倍ほど遅いが、まあ使える。
しかしVector型のものはどうしてこんなに遅いのだろう??要検討
{-# LANGUAGE PatternSynonyms #-}
{-# LANGUAGE ViewPatterns #-}
iir :: UV.Vector Double -> UV.Vector Double -> UV.Vector Double -> UV.Vector Double
iir b a x = y
where
y = iir' b a w x
w = UV.replicate mn 0
m = UV.length b
n = UV.length a
mn = max m n
iir' :: UV.Vector Double -> UV.Vector Double -> UV.Vector Double -> UV.Vector Double -> UV.Vector Double
iir' b a w v = do
case v of
Nils
-> UV.fromList []
Cons x xs
-> UV.cons y (iir' b a w' xs)
where y = UV.sum $ UV.zipWith (*) b w'
w0 = x - (UV.sum $ UV.zipWith (*) (UV.tail a) (UV.init w))
w' = UV.cons w0 (UV.init w)
uncons :: UV.Unbox a => UV.Vector a -> Maybe (a, UV.Vector a)
uncons v = do
case UV.null v of
False -> Just (UV.head v, UV.tail v)
True -> Nothing
pattern Cons x xs <- (uncons -> Just (x, xs))
pattern Nils <- (uncons -> Nothing)