(-) 怎么可能有两种不同的类型?

Tip*_*ler 17 haskell

在ghci中,当我输入

:t (-)
Run Code Online (Sandbox Code Playgroud)

找出 的类型(-),它返回

(-) :: Num a => a -> a -> a
Run Code Online (Sandbox Code Playgroud)

但是,当我写-1haskell 时返回一个数字,这似乎暗示它(-)的类型为Num a => a -> a。怎么可能(-)看似有两种不同的类型?

And*_*Ray 15

这是该语言的设计决策。-1是一个数字,但它在此上下文中的用法与函数无关(-)。(正如 Ackdari 在他们的回答中提到的,这种用法与 function 相关negate。)有几个妥协可以让这个工作:

  1. 您不能对(-)运算符进行正确的切片。作为一种解决方法,Haskell 提供了该subtract功能。

  2. 你不能写一个没有括号的负整数,除非它在赋值的开头(例如直接在=或之后->)。这会产生解析错误:

    let x = 8 * -1
    
    Run Code Online (Sandbox Code Playgroud)

    相反,它应该写成

    let x = 8 * (-1)
    
    Run Code Online (Sandbox Code Playgroud)

    但是,这很好:

    let x = -1 * 8
    
    Run Code Online (Sandbox Code Playgroud)

这些被认为是对语言设计者的合理权衡。


Ack*_*ari 8

答案已经在haskell-wiki 中描述,它指出

一元减号是 Prelude 函数的语法糖 negate

所以函数(-)始终是a - b函数,如果你像let x = -y编译器那样编写代码 ,就会将它转换为let x = negate y.


bip*_*pll 7

一元减号在 Haskell 中很特别。如报告第 3.4 节所述

特殊形式表示前缀否定,Haskell 中唯一的前缀运算符,是. 二元运算符不一定指Prelude中的定义;可能会被模块系统反弹。但是,一元总是指Prelude 中定义的函数。运算符的局部含义与一元否定之间没有联系。-enegate (e)---negate-

  • SO 不鼓励使用一句话答案,就像没有内容摘要的链接一样,因为它们可能会损坏。 (2认同)