次のプログラムは、型チェックとコンパイルを行います。
import Control.Arrow
data Ns = Na | Nb | Nc | Nd deriving Show
data Net a where
Uni :: a -> Net a
Serial :: Net a -> Net a -> Net a
Branch :: Show a => Net a -> Net (Net a, Net a)
deriving instance Show a => Show (Net a)
eval :: (Arrow a) => Net c -> a b (Net c)
eval (Uni m) = arr (const (Uni m))
eval (Serial m n) = eval m >>> eval n
--eval (Branch m) = eval m &&& eval m
example = Serial (Serial (Uni Na) (Uni Nb)) (Serial (Uni Nc) (Uni Nd))
main = do
putStrLn $ show (app (eval example, Na))
ただし、 のケースを追加しようとするとeval (Branch m)
、checking bombs out と入力します。タイプの何か
Arrow a => a b (Net d)
が期待されていますが、もちろん私が持っている方法は
Arrow a => a b (c',c'')
書き方について誰か提案がありますeval (Branch m)
か?
編集私
@sabauma のコメントに応えて、 の型シグネチャeval
を変更する必要があると思いますが、どうすればよいかわかりません。
編集Ⅱ
何が起こるべきかの例を次に示します。
branch = Branch example
app (eval branch, Na)
与えるべき、
Uni (Uni Na,Uni Na)
これが @sabauma さんの提案です。