Haskell 数据构造函数不在范围内
我正在学习Haskell并编写一个简单的程序。现在我遇到了一个问题,对我来说,这是相当令人困惑的。代码如下:Haskell 数据构造函数不在范围内,haskell,functional-programming,Haskell,Functional Programming,我正在学习Haskell并编写一个简单的程序。现在我遇到了一个问题,对我来说,这是相当令人困惑的。代码如下: data VariableName = X|Y deriving Show getValue :: VariableName -> Int getValue X = 5 getValue Y = 13 data Expression = Constant|Variable|Add|Multiply deriving Show evaluate :: Expression -&
data VariableName = X|Y deriving Show
getValue :: VariableName -> Int
getValue X = 5
getValue Y = 13
data Expression = Constant|Variable|Add|Multiply deriving Show
evaluate :: Expression -> Int
evaluate Constant x = x
evaluate Variable x = getValue x
evaluate Add x y = x+y
evaluate Multiply x y = x * y
我预计产出:
Constant 20 = 20
但是我越来越
*Main> evaluate Constant 20
<interactive>:79:1: error:
Variable not in scope: evaluate :: t0 -> Integer -> t
<interactive>:79:10: error: Data constructor not in scope: Constant
这是正确的答案。我刚开始学习Haskell,这对我来说是相当混乱的。非常感谢您的帮助。让我们看看错误: 这意味着您尚未定义
evaluate
函数和常量
构造函数(尽管您显然已经定义了)。但是你说,当你使用getValue
和X
时,这些都有效吗
这似乎不像评论中所说的那样(非常常见)多行ghci
混乱。首先,您从中得到的错误往往是非穷举模式
,这不是您得到的。其次,您的ghci
提示符显示的是*Main>
,而不是Prelude>
,这意味着您已经:加载了一个文件。所述文件根本没有定义您期望它具有的代码
我的猜测是,您在文件中编写了代码的第一部分,然后正确地加载了它,然后修改了文件并忘记了加载,因此您所做的更改从未加载
另一种可能是,您将模块Main(VariableName(..),getValue)放在文件开头的
位置,而忘记将新导出添加到其中。但这似乎不太可能
如果以上操作都不起作用,只需尝试关闭ghci
,再次打开它,然后:重新加载文件
即使解决了这个问题,您也会遇到许多其他错误,主要与括号有关。在Haskell中,当你写这样的东西时:
evaluate Constant 20
它的意思是“调用求值
函数,并向其传递两个参数:常量
和20
”。这意味着evaluate::Expression->Int->Int
,但您确实需要evaluate::Expression->Int
。所以你需要括号:
evaluate (Constant 20)
evaluate :: Expression -> Int
evaluate (Constant x) = x
evaluate (Variable x) = getValue x
evaluate (Add x y) = x+y
evaluate (Multiply x y) = x * y
这意味着“使用一个参数调用常量
构造函数20
,并将该值作为单个参数传递给evaluate
”
您不仅必须在呼叫站点进行此更改,还需要在定义中进行此更改。目前,您有:
evaluate :: Expression -> Int
evaluate Constant x = x
evaluate Variable x = getValue x
evaluate Add x y = x+y
evaluate Multiply x y = x * y
每个模式都需要不同数量的参数:前两个需要两个参数,后两个需要三个参数。问题是x
和y
被视为函数的参数,而不是构造函数。要更改此设置,需要使用括号:
evaluate (Constant 20)
evaluate :: Expression -> Int
evaluate (Constant x) = x
evaluate (Variable x) = getValue x
evaluate (Add x y) = x+y
evaluate (Multiply x y) = x * y
您需要做的最后一个更改是在构造函数定义中:您需要告诉构造函数他们首先接受参数。当前,您的数据定义如下所示(我添加了格式):
这些构造函数目前都不接受参数:它们是值(比如True
、X
、Nothing
,等等),而不是值构造函数。这不是你想要的。您需要给出每个构造函数的参数类型,如下所示:
data Expression = Constant Int
| Variable VariableName
| Add Int Int
| Multiply Int Int
deriving Show
您需要添加括号,现在看起来您使用两个变量定义了计算常数x
。此外,像常量|变量|添加|乘法
这样的表达式在一开始似乎没有多大意义,例如,我希望常量Int |变量VariableName | Add Expression Expression | Multiply Expression
,因为这些是表达式的参数。我猜您是通过ghci逐行输入此代码的,因为代码evaluate::Expression->Int;evaluate常量x=x
甚至不应与Willem的注释一起编译。@WillemVanOnsem我尝试添加所有可能的偏执论组合,但仍然会出现相同的错误:/
data Expression = Constant Int
| Variable VariableName
| Add Int Int
| Multiply Int Int
deriving Show