3

折りたたみ式を実装したい

data Constant a b = Constant a

これは私の簡単な試みです:

instance Foldable (Constant a) where
  foldr f b (Constant a) = f a b

私が理解したいコンパイルエラーの部分は次のとおりです。

Couldn't match expected type ‘a1’ with actual type ‘a’
‘a1’ is a rigid type variable bound by the type signature for
foldr :: (a1 -> b -> b) -> b -> Constant a a1 -> b

ご覧のとおり、折りたたみ関数は、a1アクセスできない定数から「ファントム型」(?) を取得します。にしかアクセスできませんa

これを解決するにはどうすればよいですか?私はかなり混乱しているので、あなたの解決策を説明してください。

コンパイルエラー全体は次のとおりです。

try2/chap20/ex1.hs:9:30: Couldn't match expected type ‘a1’ with actual type ‘a’ …
      ‘a’ is a rigid type variable bound by
          the instance declaration
          at /Users/moron/code/haskell/book/try2/chap20/ex1.hs:8:10
      ‘a1’ is a rigid type variable bound by
           the type signature for
             foldr :: (a1 -> b -> b) -> b -> Constant a a1 -> b
           at /Users/moron/code/haskell/book/try2/chap20/ex1.hs:9:3
    Relevant bindings include
      a :: a
        (bound at /Users/moron/code/haskell/book/try2/chap20/ex1.hs:9:23)
      f :: a1 -> b -> b
        (bound at /Users/moron/code/haskell/book/try2/chap20/ex1.hs:9:9)
      foldr :: (a1 -> b -> b) -> b -> Constant a a1 -> b
        (bound at /Users/moron/code/haskell/book/try2/chap20/ex1.hs:9:3)
    In the first argument of ‘f’, namely ‘a’
    In the expression: f a b
Compilation failed.
4

2 に答える 2

9

Constant a bには -sが含まれていないため、 -sbの空のリストであるかのように折りたたまれます。b

instance Foldable (Constant a) where
    foldr f z (Constant a) = z

ainは、最後のパラメーターのみにConstant a b関係するため、インスタンスには関係ありません。したがって、定義Foldableで実際に使用することはできません。a

于 2016-05-24T17:46:57.040 に答える
2

唯一の可能性は次のとおりだと思います。

data Constant a b = C a

-- foldMap :: Monoid m => (b -> m) -> t b -> m
instance Foldable (Constant a) where
  foldMap f (C a) = mempty

これは簡単な解決策です。

この定義に対してなぜそれを行うことができるのかを理解することは有益かもしれません:

data Constant' a b = C' b

-- foldMap :: Monoid m => (b -> m) -> t b -> m
instance Foldable (Constant' a) where
  foldMap f (C' a) = f a

ここにtあるConstant' aので、

  • タイプt bConstant' a bです。この型の値は、 typeの値の構造C bvalを持っています。bvalb
  • ftype を持っているので、にb -> m適用できますfbval

ただし、それ以外の場合は、 frombに適用する値がないfため、できる最善の方法は returnmemptyです。

于 2016-05-24T17:45:13.020 に答える