4

在我的作业中,我必须按如下方式定义逻辑运算符:
使用此数据结构:

data MyBool = Cierto|Falso deriving (Show,Eq) -- Cierto = True and Falso = False
data PQR = A|B|C|D|E|F|G|H|I|J|K|L|M|N|O|P|Q|R|S|T|U|V|W|X|Y|Z deriving (Show,Eq)
data Formula = VarProp PQR 
             |Neg Formula -- logic not
             |Formula :|: Formula -- logic or
             |Formula :&: Formula -- logic and... etc
             |Formula :->: Formula
             |Formula :<->: Formula deriving (Show,Eq)

而且我必须定义函数来告诉我给定公式是真还是假,例如,如果我写(Cierto :&: Falso)答案必须是:Falso

根据我的老师的说法,在这种情况下必须调用函数:&:并且必须接收MyBool类型,所以我尝试像这样实现:

infixr 3 :&:
(:&:) :: MyBool -> MyBool -> MyBool
Cierto :&: x = x
Falso :&: x = Falso

但是当我尝试加载它时,它说:

Invalid type signature

我不知道我在这里做错了什么。

4

2 回答 2

5

问题是:函数前面的 a 表示数据构造函数;这就像以大写字母开头。您应该重命名:&:|&|.

编辑:没关系,我刚刚意识到你真正想要完成的事情。

:&:应该采用两个sMyBool并创建 aFormula而不是另一个MyBool。您尝试将其实现:&:为函数;它是一个数据构造函数。您已经在data Forumla = ...表达式中声明了它。

您根本不需要函数声明。完全删除以下代码块:

infixr 3 :&:
(:&:) :: MyBool -> MyBool -> MyBool
Cierto :&: x = x
Falso :&: x = Falso

然后,您应该能够使用:&:两个MyBools 并创建一个Formula而不添加任何其他代码。

然而,:&:实际作用于MyBools 还不够普遍。我们希望能够同时使用表达式和布尔值。因此,您实际上想要:&:组合Formulas. 这就是您的代码已经完成的工作。您缺少的是一个像Literal这样的构造函数,它接受 aMyBool并返回Formula表示该布尔值的 a 。

于 2011-12-05T06:38:11.350 回答
5

你的教授强迫你为布尔运算符创建一个抽象语法树(AST)。如果您在此之前还没有听说过“抽象语法树”这个词,那么是时候问问某人到底发生了什么。

您实际上想要做的是编写一个eval带有 type 的函数(称为 say )Formula -> Formula。在查看定义时,我也相信您已经留下了一条线data Formula,应该是VarLiteral MyBool. 看起来您的 AST 是一种编写程序的方式,它在MyBool's 上运行并支持典型的布尔运算以及:->:分配(?)。

我已经在 Haskell 中编写了一些 AST 评估器(尽管没有这么老土的 :)),感觉您的问题中缺少一些内容。鉴于我面前的情况,我对你最好的建议是说这个作业比你想象的要抽象一个层次。

祝你好运

于 2011-12-05T07:25:43.607 回答