Haskell中的newtype行为

6

我发现我可以执行1 :: Product Int,结果会得到Product {getProduct = 1}

Product是在Data.Monoid中定义的一个newtype。然后我尝试像这样定义我的自己的newtype

newtype Stuff a = Stuff {getStuff :: a} deriving (Show)

但是如果我尝试执行 1 :: Stuff Int,就会出现错误:

<interactive>:20:1: error:
* No instance for (Num (Stuff Int)) arising from the literal `1'
* In the expression: 1 :: Stuff Int
  In an equation for `it': it = 1 :: Stuff Int

我需要给 a 加上 Num 约束吗?为什么这样做不起作用?

1个回答

15
只有当 TNum 的实例时,才能执行 1 :: T。因为 Product 定义了一个实例 instance Num a => Num (Product a)(即如果 aNum 的实例,则 Product a 也是 Num 的实例),所以 1 :: Product Int 是可行的。

我需要在 a 上放置 Num 约束吗?

你需要为 Stuff Int(或更好地为 Num a => Stuff a)定义一个 Num 实例。

你可以手动进行定义(使用 instance),也可以使用 deriving NumGeneralizedNewtypeDeriving 扩展自动定义一个 Num 实例,为给定的 a 定义与 Num 实例完全相同的行为的 Num 实例。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接