How does Frege generalize numeric literals?

It seems like Frege can appreciate

1/2 

to return a double value of 0.5.

Literal 1 is of type Int . It seems that it is advancing to Double , which is a type in the Real class and therefore knows the / operator. How did this happen? Does the Haskell approach silently replace literal 1 with fromInt 1 or is something else happening? How is Double selected as a Real instance to use here? Is there a list of default instance types, for example in Haskell?

+6
source share
1 answer

Simple decimal literals without a type indicator (i.e., one of the letters lndf) do not have an automatic Int type in Frege.

They will get the assigned type, which you probably want, and the literal will be adapted accordingly. That's why they are called DWIM letters (what I mean).

This is mentioned in the Haskell Differences document. Of course, this should also be in the language reference guide. If it is not there, it should be because the author is very lazy.

In short, DWIM works as follows: when a type controller sees a literal for the first time, it simply assigns it a type variable, as well as a Num constraint for that type variable. Later, in the second pass, he finds all the DWIM literals. And now the type variable is in one of the following states:

  • unified with some type, for example Long, Double or the like. The literal will be typed accordingly.
  • Unified with another type: this is a mistake.
  • Unified with a type variable from a type signature: the literal is replaced by the fromInt application in the literal entered as Int.
  • Not unified at all: if a variable of a type is bounded (by a subtype) of Real, type is Double, otherwise Int.

In your example, literals are printed by Double due to the restriction of the Real division operator.

A similar approach is taken for literals with a decimal point, however, they begin with a real limit and can thus end in either Float or Double or application ofDouble.

Please note that, with the exception of case 3, no type or type conversion occurs at startup.

The reason literals are usually not overloaded, as in Haskell, is to avoid unnecessary class restrictions, since their implementation leads to expensive code. Also, since we have no restriction on monomorphism, you could have polymorphic constants by chance. (Think fibs = 1: 1: ...)

With DWIM literals, you get monomorphic constants and functions, unless otherwise required with type annotation.

+3
source

Source: https://habr.com/ru/post/989206/


All Articles