2016-03-16 2 views
1

Рассмотрим:Почему результат функции (/) также может быть интегральным?

> :t (/) 
(/) :: Fractional a => a -> a -> a 

и

> :t (round 10/100) 
(round 10/100) :: (Fractional a, Integral a) => a 

Как можно (/) приводит к Integral?

+6

он ограничен ** как ** 'Fractional' ** и **' Integral' - 'Integral', потому что вы использовали' round :: (Интеграл b, RealFrac a) => a -> b' и ' Франкал' из-за '(/)' – Carsten

+0

@ Карстен Я думал: t показывает тип конечного результата. Почему он рассматривает некоторые промежуточные типы? –

+2

он делает - и, конечно же, он должен собрать все ограничения для * end-result * - см.: 'Fractional' в одиночку будет недостаточно, так как' round 10' может производить только 'Integral a' - see: a ' Fractional' не обязательно должен быть 'Integral' – Carsten

ответ

7

Я считаю, что вы неправильно понимаете тип результата

result :: (Fractional a, Integral a) => a 

Этого типа является «договором» между пользователем result и реализатором result. Давайте считать друг от друга:

  1. пользователя должен сначала выбрать тип a
  2. пользователя затем должен доказать, что выбранный a принадлежит к классам Fractional и Integral. Грубо говоря, это означает, что пользователь должен предоставить определение для методов таких классов.
  3. И наконец, изготовитель предоставит значение типа a.

Часть 2 является решающим шагом. Как видим, тип resultне обещает построить некоторое значение, тип которого является дробным и интегральным. В противном случае: требует, чтобы, что любой, кто захочет использовать это значение result, должен найти такой тип.

Конкретно это означает, что result непригодно. GHC не вызывает ошибку типа, потому что у нее нет глубоких знаний о предполагаемом значении классов типов. Действительно, с чисто теоретической точки зрения можно было определить нестандартный тип и предоставить дробные/интегральные экземпляры, например.

data A = A0 | A1 | A2 

instance Num A where 
    ... 
instance Fractional A where 
    ... 
instance Integral A where 
    ... 

с некоторыми странными реализациями, такими как выполнение дробных операций по модулю 3, но не интегральные операции.

В любом случае, поскольку может быть определено что-то вроде A, GHC не может отказаться от вышеуказанного типа.

Смежные вопросы