【问题标题】:How to create a type instance of class in haskell?如何在haskell中创建类的类型实例?
【发布时间】:2016-12-05 04:22:07
【问题描述】:

我是 Haskell 的新手。

我正在寻找是否有任何方法可以创建类类型的实例。

有什么方法可以在不使用 data 或 newtype 的情况下让这段代码正常工作?

type N = ∀n. (n -> n) -> n -> n

instance Printable N where
        print :: N -> IO ()
        read  :: String -> N 

当我尝试在 GHCi 中加载模块时,它告诉我:

Illegal polymorphic or qualified type: N
In the instance declaration for ‘Printable N’

【问题讨论】:

  • 你为什么不想使用newtype
  • 如果我使用 newtype 或 data 我需要写类似:newtype N = N (n -> n) -> n -> n),然后重写像 (+) (N a) (N b) = stuff 这样的函数而不是 (+) = \a b -> stuff 而不拆箱 a 或 b。
  • 在当前的 GHC 中最好避免含糊不清。没有办法,只能使用newtypedata。 (同时查找安全强制,这使得 newtypes 在某些情况下更易于处理)。

标签: haskell types church-encoding


【解决方案1】:

你在那里写的看起来很像一个类声明,而不是一个实例。也许你是这个意思?

class Printable n where
  print :: n -> IO ()
  read  :: String -> n

请注意,n 必须是小写的,因为这是您要量化类的 类型变量。如果你真的想定义一个实例,那么你,实例化 nN

instance Printable N where
  print n = ...
  read str = ...

此时类型签名都是固定的(来自类定义),您需要编写的是这些函数的实际绑定,因此它必须是=,而不是@987654327 @。

问题是:为什么还需要自己的课程?它只会导致与已经在前奏中的标准函数printread 发生名称冲突。您实际上应该做的是用您的 N 类型实例化 那些标准类,即

instance Show N where
  show n = ...
instance Read N where
  readsPrec _ str = ...

也就是说,要回答您提出的实际问题:,不可能为像 ∀ n . (n->n) -> n->n 这样的多态类型合理定义 任何 实例.编译器应该如何将其与更具体的类型(如(Int->Int) -> Int->Int)或更一般的类型(如∀ n m . (n->m) -> n->m)区分开来?这是相当绝望的。 正确 的做法是将其包装在一个新类型中;这隐藏了通用量化并允许编译器正确区分 N 与其他类型。

或者,您可以直接编写接受/产生N单态函数

showChurch :: N -> String
showChurch n = ...
readsPrecChurch :: Int -> ReadS N
readsPrecChurch _ str = ...

其实后一个对于类型系统来说已经太多了:ReadS N 的缩写

readsPrecChurch :: Int -> String -> [(∀ n . (n->n) -> n->n, String)]

列表中的通用量化?哦哦。那是一种含蓄的类型。 GHC 确实有一个-XImpredicativeTypes 扩展,但它并没有真正起作用。

同样,不要公开使用多态类型来避免这些问题。 Rank-N 类型(尤其是镜头)有一些很好的用途,但大多数时候它们完全是多余的和不必要的。确实没有充分的理由实际使用这样的教堂数字。

newtype N = Church { getChurch :: ∀ n . (n->n) -> n->n }

将允许您毫无问题地定义任意实例或函数。而且,实际上,只是做

type N = Int

对于整数的所有标准实例当然也一样好......

【讨论】:

  • 对不起,我的问题解释得很糟糕,但您仍然回答正确,非常感谢!
猜你喜欢
  • 2015-02-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-03-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-08-12
相关资源
最近更新 更多