続・畳み込みのコーナー
foldl1 と foldr1
foldl と foldr に似ているが、初期アキュムレータを明示的に与える必要がない
最大値を求める maximum を実装すゆ
maximum' :: (Ord a) => [a] -> a maximum' = foldl1 max
実行結果
*Main> maximum' [1,2,3,4,5] 5
foldl1 と foldr1 で定義した関数は、引数のリストに少なくとも1つ要素が含まれていることを前提にしているので、空リストに対して呼び出すとランタイムエラーが発生する。一方、foldl と foldr で定義した関数は空リストに対しても正しく動く。
畳み込みの例
reverse を実装
reverse' :: [a] -> [a] reverse' = foldl (flip (:)) []
実行結果
*Main> reverse' [1,2,3,4,5] [5,4,3,2,1]
product を実装
product' :: (Num a) => [a] -> a product' = foldl1 (*)
実行結果
*Main> product' [1,2,3,4] 24
filter を実装
filter' :: (a -> Bool) -> [a] -> [a] filter' p = foldr (\x acc -> if p x then x : acc else acc) []
実行結果
*Main> filter' (>2) [1,2,3,4] [3,4]
last を実装する
last' :: [a] -> a last' = foldl1 (\_ x -> x)
実行結果
*Main> last' [1,2,3,4] 4
所感
maximum'
が引数をとらないのは、foldl1 max
がリストを引数に取る関数を返すからか...20分くらい悩んだ...
部分適用の頭がまだできてないな。まあ、あんまり気張らずやっていこう。

- 作者: MiranLipovaca
- 出版社/メーカー: オーム社
- 発売日: 2017/07/14
- メディア: Kindle版
- 購入: 4人 クリック: 9回
- この商品を含むブログを見る