Most of it is safety, you can work around it by excluding type definitions, 
or using magical type definition, in fact take this example with magical 
type definitions (put it in http://elm-lang.org/try or so):
```elm
import Html exposing (div, br, text)

filterIfAbove  : List comparable -> comparable -> List comparable
filterIfAbove  l above =
  let
    aux : comparable -> Bool
    aux v = v <= above
  in List.filter aux l

main =
  div []
  [ br [] [], text (toString (filterIfAbove [1,2,3,4,5] 3))
  , br [] [], text (toString (filterIfAbove [1.1,2.2,3.3,4.4,5.5] 3.0))
  , br [] [], text (toString (filterIfAbove ["Hello","World"] "Test"))
  ]
```
This prints out:
```
[1,2,3]
[1.1,2.2]
["Hello"]
```
Which is entirely expected, so let's make a new function that acts a little 
bit different:
```elm
addTogetherIfAbove : List comparable -> comparable -> comparable
addTogetherIfAbove l above =
  let
    aux : comparable -> Bool
    aux v = v <= above
  in List.filter aux l |> List.sum
```
Now remember, elm does not have real typeclasses, things like comparable 
are breaking the type system since they are internal magic, so with magic 
this compiles!  And it outputs what I'd expect:
```elm
main =
  div []
  [ br [] [], text (toString (addTogetherIfAbove [1,2,3,4,5] 3))
  , br [] [], text (toString (addTogetherIfAbove [1.1,2.2,3.3,4.4,5.5] 3.0))
  , br [] [], text (toString (addTogetherIfAbove ["Hello","World"] "Test"))
  ]
```
Output:
```
6
3.3000000000000003
"Hello0"
```
It outputs entirely wtf.

However I got side-tracked by the sudden wtf, back to the issue.  ^.^
Define this function again without typing:
```elm
addTogetherIfAbove l above =
  let
    aux v = v <= above
  in List.filter aux l |> List.sum
```
It compiles and works fine (and will properly give an error message if you 
pass in a list of strings),

Using this code in elm 0.17, before this feature was added:
```elm

import Html exposing (div, br, text)

addTogetherIfAbove : List a -> a -> a
addTogetherIfAbove l above =
  let
    aux : a -> Bool
    aux v = v <= above
  in List.filter aux l |> List.sum

main =
  div []
  [ br [] [], text (toString (addTogetherIfAbove [1,2,3,4,5] 3))
  , br [] [], text (toString (addTogetherIfAbove [1.1,2.2,3.3,4.4,5.5] 3.0))
  ]
```
You'd get this for this the compile output in 0.17:
```
-- TYPE MISMATCH ------------------------------------------------------ 
main.elm

The type annotation for `aux` does not match its definition.

6|     aux : a -> Bool
             ^^^^^^^^^
The type annotation is saying:

    a -> Bool

But I am inferring that the definition has this type:

    comparable -> Bool

Hint: A type annotation is too generic. You can probably just switch to the 
type
I inferred. These issues can be subtle though, so read more about it.
<https://github.com/elm-lang/elm-compiler/blob/0.17.1/hints/type-annotations.md>
```
And, uh, this is because Elm does not have HKT's, hrmm, how to show this 
without HKT's..

Oh fascinating, tried this code:
```elm

import Html exposing (div, br, text)

addTogetherIfAbove : List a -> a -> a
addTogetherIfAbove l above =
  let
    aux : comparable -> Bool
    aux v = v <= above
  in List.filter aux l |> List.sum

main =
  div []
  [ br [] [], text (toString (addTogetherIfAbove [1,2,3,4,5] 3))
  , br [] [], text (toString (addTogetherIfAbove [1.1,2.2,3.3,4.4,5.5] 3.0))
  ]
```
And got this from the compiler:
```
elm-make: It looks like something went wrong with the type inference 
algorithm.

Unable to generalize a type variable. It is not unranked.

Please create a minimal example that triggers this problem and report it to
<https://github.com/elm-lang/elm-compiler/issues>
elm-make: thread blocked indefinitely in an MVar operation
```
Well that is new, elm is not enforcing that the type `a` must be comparable 
due to its usage in the `List.filter` call, and it cannot enforce that it 
is a `number` because of the `List.sum` call, and so it croaks with a new 
error message, fun...

Well in general there are usages where if you leave the type information 
out, it works, but if you try to type it then you absolutely cannot.  A 
more simple example might just be:
```elm
import Html exposing (div, br, text)

blah : a -> b -> (a, b)
blah a b =
  let
    aux : a
    aux = a
  in (aux, b)

main =
  div []
    [ br [] [], text (toString (blah 2 3))
    ]
```
Will compile fine in 0.18, but gives this error in 0.17:
```
The type annotation for `blah` does not match its definition.

3| blah : a -> b -> (a, b)
          ^^^^^^^^^^^^^^^^
The type annotation is saying:

    a -> b -> ( a, b )

But I am inferring that the definition has this type:

    a -> b -> ( c, b )

Hint: A type annotation is clashing with itself or with a sub-annotation. 
This
can be particularly tricky, so read more about it.
<https://github.com/elm-lang/elm-compiler/blob/0.17.1/hints/type-annotations.md>

Detected errors in 1 module.
```



On Tuesday, November 15, 2016 at 11:43:58 AM UTC-7, John Orford wrote:
>
> > And there are certain classes of typed problems that are impossible 
> without this feature, so it is highly useful!
>
> Can you expand on this? I imagine it's expressions all the way down and 
> type inference is still possible... so imagine it's a nice-to-have rather 
> than must-have.
>
> Would like to understand more basically!
> On Tue, 15 Nov 2016 at 17:40, OvermindDL1 <[email protected] 
> <javascript:>> wrote:
>
>> On Tuesday, November 15, 2016 at 9:30:23 AM UTC-7, Max Goldstein wrote:
>>>
>>> My impression is that it's a Haskell extension that's very commonly 
>>> used. In the process of upgrading, I uncommented some signatures only for 
>>> the compiler to tell me that they are incorrect, so this feature has been 
>>> useful already.
>>
>>
>> Oh it is very useful!  And there are certain classes of typed problems 
>> that are impossible without this feature, so it is highly useful!
>>
>> An example of usage in OCaml anyway (since I have a shell of it up right 
>> now):
>> ```ocaml
>> let f (x : 'x) =
>>   let a (y : 'x) = ()
>>   in a
>>
>> let b = f 42 3
>> ```
>> That compiles right, changing b to this though:  let b = f 42 3.14
>> Causes this error:
>> ```
>> Line 6, 14: Error: This expression has type float but an expression was 
>> expected of type
>>          int
>> ```
>> Where this compiles fine (and may not only be entirely unexpected but 
>> could hide major bugs later in the program!):
>> ```ocaml
>> let f x =
>>   let a y = ()
>>   in a
>>
>> let b = f 42 3.14
>> ```
>>
>> -- 
>> You received this message because you are subscribed to the Google Groups 
>> "Elm Discuss" group.
>> To unsubscribe from this group and stop receiving emails from it, send an 
>> email to [email protected] <javascript:>.
>> For more options, visit https://groups.google.com/d/optout.
>>
>

-- 
You received this message because you are subscribed to the Google Groups "Elm 
Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/d/optout.

Reply via email to