Есть ли способ реализовать ограничения в классах типов Haskell?

StackOverflow https://stackoverflow.com/questions/2253235

Вопрос

Есть ли какой- нибудь способ (Любой способ) реализовать ограничения в классах типов?

В качестве примера того, о чем я говорю, предположим, что я хочу реализовать Group как класс типов.Таким образом, тип был бы группой, если бы существовало три функции:

class Group a where
    product :: a -> a -> a  
    inverse :: a -> a 
    identity :: a

Но это не какие-либо функции, но они должны быть связаны некоторыми ограничениями.Например:

product a identity = a 
product a (inverse a) = identity
inverse identity = identity

и т.д...

Есть ли способ применить такого рода ограничение в определении класса, чтобы любой экземпляр автоматически наследовал его?В качестве примера предположим, что я хотел бы реализовать группу C2, определенную:

 data C2 = E | C 

 instance Group C2 where
      identity = E 
      inverse C = C

Эти два определения однозначно определяют C2 (приведенные выше ограничения определяют все возможные операции - фактически, C2 является единственной возможной группой с двумя элементами из-за ограничений).Есть ли способ заставить это работать?

Это было полезно?

Решение

Есть ли способ обеспечить соблюдение такого рода ограничений?

Нет. Лоты множество людей просили об этом, включая знаменитого Тони Хоара, но на горизонте пока ничего не появляется.

Эта проблема была бы отличной темой для обсуждения для Простое число Хаскелла Группа.Если кто-то выдвинул хорошее предложение, его, вероятно, можно найти там.

P.S.Это важная проблема!

Другие советы

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

prop_EqNeq x y = (x == y) == not (x != y)

Конечно, вызов этого теста по-прежнему зависит от автора экземпляра.

Было бы интересно сделать это для законов монады.

Классы типов могут содержать определения, а также объявления.Пример:

class Equality a where
    (?=), (!=) :: a -> a -> Bool

    a ?= b = not (a != b)
    a != b = not (a ?= b)

instance Eq a => Equality a where
    (?=) = (==)

test = (1 != 2)

Вы также можете указать специальные ограничения (давайте назовем их законы) в обычном Haskell, но не гарантируется, что компилятор будет их использовать.Распространенным примером являются монадические законы

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top