Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can (-) seemingly have two different types?

Tags:

haskell

In ghci, when I type

:t (-)

to figure out the type of (-), it returns

(-) :: Num a => a -> a -> a

However, when I write -1 haskell returns a number, which seems to imply that (-) is of type Num a => a -> a. How can (-) seemingly have two different types?

like image 331
TippFehler Avatar asked Apr 17 '20 13:04

TippFehler


2 Answers

This was a design decision in the language. -1 is a number, but its usage in this context is not related to the function (-). (As Ackdari mentions in their answer, this usage is related to the function negate.) There are a couple compromises that allow this to work:

  1. You cannot take a right slice of the (-) operator. As a workaround, Haskell provides the subtract function.

  2. You cannot write a negative integer without parentheses unless it is at the beginning of an assignment (e.g. directly after = or ->). This produces a parse error:

    let x = 8 * -1
    

    Instead, it should be written as

    let x = 8 * (-1)
    

    However, this is fine:

    let x = -1 * 8
    

These were considered to be reasonable tradeoffs to the designers of the language.

like image 168
Andrew Ray Avatar answered Oct 22 '22 19:10

Andrew Ray


The answer is already descirbed in the haskell-wiki, it states

The unary minus is syntactic sugar for the Prelude function negate

so the function (-) is always the a - b function and if you write code like let x = -y the compiler will translate it to let x = negate y.

like image 30
Ackdari Avatar answered Oct 22 '22 19:10

Ackdari