Haskell,句法简化括号

时间:2018-04-30 10:36:18

标签: haskell brackets reduction

我知道无意义的代码,但试图在我的大脑中印上类词类等。

问题:如何摆脱以下功能中的括号?如果我在任何地方使用它,'$'会抛出错误。

data Vector = Vector XY XY deriving (Show)
data XY = XY (Float , Float) deriving (Show)
vector (Vector (XY (x1,y1)) (XY(x2,y2))) = [(x1,y1),(x2,y2)]

2 个答案:

答案 0 :(得分:4)

$运算符

$ 不是 Haskell语法的一部分。它是内置的运算符 ($) :: (a -> b) -> a -> b,运算符定义为inxfixr 0,具有实现:

($) :: (a -> b) -> a -> b
($) f x = f x

因此,它将函数f和值x作为输入,并且基本上返回应用于f的{​​{1}}。由于它具有优先级x,这意味着它绑定非常低,因此如果你写

0

你真的写道:

f . g $ x + 2

这是一个详细的形式:

($) ((.) f g) ((+) x 2)

或:

((.) f g) ((+) x 2)

因此它可以用作“技巧”来强制Haskell自己添加括号。由于它是一个运算符,而不是语法的一部分,因此它不适用于其他位置,如类型签名,模式,派生子句。

当然,操作员也有其他目的。例如,我们可以在其他更高阶函数中使用它(例如(f . g) (x + 2) ,其中包含函数列表zipWith ($)和值列表[f1, f2, ...]并返回列表[x1, x2, ...]

缩小括号数

然而,我们可以最小化括号的数量。例如[f1 x1, f2 x2, ...]子句需要括号,如果你只派生一个单个类型类,那么我们可以这样写:

deriving

此外,在函数声明中,您解压缩元组,但是将元组元素重新替换为基本相同的元组中的元组元素。我们可以通过绑定data Vector = Vector XY XY deriving Show data XY = XY (Float , Float) deriving Show 构造函数的内容来减少表达式(并减少解包和重新打包的数量):

XY

答案 1 :(得分:2)

使用类型的记录语法

data XY = XY {xy :: (Float, Float)} deriving (Show)
data Vector = Vector {v1 :: XY, v2 :: XY} deriving (Show)

你可以在没有明确模式匹配的情况下编写vector

vector :: Vector -> [(Float, Float)]
vector v = map xy [v1 v, v2 v]