象限赋予功能时出错

时间:2016-03-14 19:32:35

标签: function haskell guard-statement

我尝试在输入x和y坐标时创建一个函数来给出象限名称。但是,我收到错误: "解析输入'='

时的错误

失败,模块加载:无。"

我尝试添加" |否则.."但那仍然没有奏效。我确保我涵盖了x和y的所有可能性。

data Quadrants = Origin |
                 Quadrant_I | Quadrant_II | Quadrant_III | Quadrant_IV |
                 X_Axis_Positive | X_Axis_Negative | Y_Axis_Positive | Y_Axis_Negative
  deriving (Show, Eq)
quadrant :: Float -> Float -> Quadrants
quadrant x y
    |x>0 && y>0 = Quadrant_I
    |x<0 && y>0 = Quadrant_II
    |x<0 && y<0 = Quadrant_III
    |x>0 && y<0 = Quadrant_IV
    |x=0 && y=0 = Origin
    |x>0 && y=0 = X_Axis_Positive
    |x<0 && y=0 = X_Axis_Negative
    |x=0 && y>0 = Y_Axis_Positive
    |x=0 && y<0 = Y_Axis_Negative

3 个答案:

答案 0 :(得分:4)

x=0

=用作keyword for definitions。由于此时您不能(并且不希望)将x定义为0,因此会出现解析错误。您正在寻找的是比较功能。在Haskell中,这是==,请参阅Data.Eq

答案 1 :(得分:1)

我认为如果你将每个坐标的符号分离为中间类型的另一种类型和模式匹配,我认为你可以简化结构,即

data Sign = Negative | Zero | Positive
sign x | x==0 = Zero
       | x>0  = Positive
       | otherwise = Negative

然后

quadrant :: Float -> Float -> Quadrants
quadrant x y = go (sign x) (sign y)
       where go Zero Zero = Origin
                Zero Positive = Y_Axis_Positive
                ...

或者您可以省去象限类型的需要,而是可以使用元组(符号,符号),这可能对后续步骤更有用。

答案 2 :(得分:0)

这主要是karakfa非常好的答案的重复,只是指出Haskell带有与Sign同构的数据类型,即Ordering

quadrant :: Float -> Float -> Quadrants
quadrant x y = go (compare x 0) (compare 0 y)
               where go EQ EQ = Origin
                     go EQ GT = Y_Axis_Positive
                     go EQ LT = Y_Axis_Negative
            ...

您的Quadrants类型与Ordering个值对是同构的,这意味着您可以编写类似

的代码
type Quadrant = (Ordering, Ordering)
origin = (EQ, EQ)
quadrant_i = (GT, GT)
-- etc

quadrant :: Float -> Float -> Quadrant
quadrant x y = ((compare x 0), (compare y 0))

这样做的缺点是需要使用语言扩展来进行模式匹配,例如origin而不是直接(EQ, EQ)