我正在做SAT的一些事情,我希望同时拥有“和”和“或”条款。
type AndClause = [Literal]
type OrClause = [Literal]
但是当我使用它时我遇到了问题:
instance Satisfiable AndClause where ...
instance Satisfiable OrClause where ...
给我“重复的实例声明”。它们是类型,而不是数据或类型构造函数,所以我认为我不能使用newtype来做我想要的。有没有解决方案?
答案 0 :(得分:22)
问题是你似乎想要同时发生两件相互冲突的事情:
基于域名,我认为您当然不希望使用类型同义词,并且您确实需要实际的新类型(带有类型构造函数)。如果AndClause
是[Literal]
的同义词,而OrClause
是[Literal]
的同义词,则传递属性AndClause
和OrClause
是相互同义。因此,编译器没有理由区分它们(因此,不存在多态性)。
你真正想要的是两种表现不同的不同类型,newtype
可以做得很好:
newtype AndClause = AndClause [Literal]
newtype OrClause = OrClause [Literal]
instance Satisfiable AndClause where
satisfy (AndClause l:ls) = --...
instance Satisfiable OrClause where
satisfy (OrClause l:ls) = --...
但是,更好的想法可能是使其成为代数数据类型:
data Prop = And [Literal]
| Or [Literal]
instance Satisfiable Prop where
satisfy (And l:ls) = --...
satisfy (Or l:ls) = --...
(请注意,我输入的是远离编译器,但基本上应该是正确的。)