傻重复记录的字段错误
问题描述:
考虑以下几点:傻重复记录的字段错误
{-# LANGUAGE DuplicateRecordFields #-}
data A = A { name :: String }
data B = B { name :: String }
main = print $ name (A "Alice")
在编译时,我收到以下消息(GHC上8.0.2)
duplicatedrecords.hs:7:16: error:
Ambiguous occurrence ‘name’
It could refer to either the field ‘name’,
defined at duplicatedrecords.hs:5:14
or the field ‘name’, defined at duplicatedrecords.hs:3:14
但是如果我修改main
线如下:
main = print $ name ((A "Alice") :: A)
编译成功进行。
这是为什么?类型签名:: A
对我来说似乎是多余的,因为A
构造函数肯定会告诉编译器(A "Alice")
的类型为A
。但由于某种原因,它有所作为。为什么是这样的,有没有一种方法可以让我编译而不用在任何地方乱扔额外的类型签名?
注:
值得一提的是,以下编译罚款:
data A = A { a_name :: String }
data B = B { b_name :: String }
class Name t where
name :: t -> String
instance Name A where name = a_name
instance Name B where name = b_name
main = print $ name (A "Alice")
我们甚至可以走得更远如下,让不同的结果类型:
{-# LANGUAGE TypeFamilies #-}
data A = A { a_name :: String }
data B = B { b_name :: Int }
class Name t where
type family T t
name :: t -> T t
instance Name A where
type T A = String
name = a_name
instance Name B where
type T B = Int
name = b_name
main = print $ name (A "Alice")
似乎就像GHC一样,必须为每个数据类型中的每个记录的每个唯一记录名称和一个实例机械地添加一个类。这将意味着name x == name y
并不意味着x
和y
的类型是相同的,但是我期望在使用这个扩展的时候。
只是想知道是否有什么棘手的问题,我在这里错过了关于实现或者它只是需要有人做到这一点?
答
-XDuplicateRecordFields
当前不会从参数中推断出类型。
请参阅GHC user guide section about this extension。
但是,我们不推断确定数据类型的参数类型,或者有任何方式将选择推迟到约束求解器。因此以下是不明确的:
但事情正在改善。因此,我们可以预期,最终获得所需的行为:
感谢Shersh,这就是我正要说。目前的行为是克林顿寻找途中的中途之家。同时你可以看看他的镜头包。 – AntC