Обновить
59

Пользователь

22
Подписчики
Отправить сообщение
Не комплируется:

You can only compile modules without unsolved metavariables
or termination checking problems.
Хотя что-то не могу найти подтверждения, так что скорее всего соврал относительно Haskell.
Тем не менее всякие структуры данных и алгоритмы работы с ними 1 в 1 пишутся на той же Agda.
А нам не нужно для произвольных, нам для конкретных.
Завершимость тоже не определишь в общем случае, что не помешало определить её для, ЕМНИП, 80% стандартной библиотеки Haskell.
Разумеется. Однако там есть возможность устроить «вечный цикл» через корекурсию, но это сразу видно по коиндуктивному типу.
Ну, Agda, например, не зависает :)
Правда, доказательства там для подмножества Haskell, так как бесконечный список, например, не отсортируешь вообще.

На Agda можно заниматься тем же самым вручную. Там first-class доказательства, основанные на изоморфизме Карри-Говарда.
Например для Haskell есть Zeno, генерирующий доказательство на Isabelle. По ссылке уже написан тестовый код на Haskell и утверждения, которые надо доказать. По умолчанию там выбран isorts_sorts:
prop_isort_sorts (xs :: [Nat]) 
  = proveBool (sorted (isort xs))


Я ради интереса вбивал туда монадические законы для Maybe, List и т.п.
Которые слизаны с ФП как раз. Но я отвечал на «Объясните мне, как элегантно решить данную задачу без ООП». Однако я не согласен с утверждением «И в ООП нет ничего, что позволяет решать ту или иную задачу элегантнее», тем не менее всё вполне решается и без наличия в самом языке классов или методов. Особенно если учесть, что ООП — это подход. Тот же Erlang вообще вполне себе ООП (процессы обмениваются сообщения), и на том же Haskell можно сделать ООП через зелёные потоки. Так что сам подход иногда очень хорошо ложится на задачу, но это не значит, что ООП нужен везде, и уж тем более не значит, что без поддержки в языке классов в нём будет что-либо неудобно.
К сожалению, у меня нет времени тут расписывать всё это.
Это «интерфейс», реализуя который мы получаем функцию сравнения двух объектов.
Отличие от x.isEqual(y) в том, что isEqual реализован для object и принимает object, поэтому равенство типов приходится проверять внутри самому. Тут же == гарантированно принимает значения одного типа. А вот какого именно — уже неважно.
И как эту перегруженную функцию передать в другую функцию? Не одну из, а все скопом.
Ну и как реализовать на ООП вот такое:
class Eq a where
  (==) :: a -> a -> Bool


Через isEqual что ли с принятием 2-х object?
Я же написал выше про классы типов, они шире интерфейсов.
Что такое реализовать интерфейс? Предоставить набор функций над конкретным типом данных. В ФП это делается тривиально.
Я даже не знаю, как ответить на этот столь общий вопрос. Наверное «так же, как и везде». Расширяемое ПО пишут и на Си, и на Erlang, и на OCaml.
Нет, я предлагаю ознакомиться с тем, как реализована инкапсуляция и полиморзфим в неООП. Тогда вы сами поймете, как эти задачи решаются там.
То же, что вы сейчас написали выше, не дико не удобно, а ровно то ООП и есть, только с другим синтаксисом.
Existentials решают эту проблему
Правда на деле это крайне редко нужно, потому что на ФП разрабатывают иначе.
Что значит «выводилка загрустит»? Работать перестанет? Станет тормозить?
По опыту скажу, что в реальной программе куда быстрее загрустят люди, которым информация о типе многое говорит, и хорошо было бы этот тип видеть глазами. А вот выводилка чувствует себя хорошо.
Пока вы формулируете задачу в терминах ООП через «я создаю классы» и «у них есть методы», я не смогу вам ответить, так как в ФП нет методов, а есть функции, поэтому сама задача «три класса с одинаковыми методами» там звучит крайне странно.

Вот, например, хотим мы уметь сравнивать числа, строки, whatever you want, в Haskell для этого существует класс типов Eq, это похоже на интерфейсы, но несколько мощнее
class Eq a where
  (==) :: a -> a -> Bool
-- обратите внимание на то, что с обоих сторон от == значения одного типа
-- т.е. написать 1 == "asd" нельзя, а вот 1 == 2 и "sdd123" == "34sdf" - можно


Причём реализовано это через обычную структуру, вот такую:
data Eq a = Eq { (==) :: a -> a -> Bool }


Разница только в том, что во втором случае мне придётся её передавать в функции явно, а класс типов передаётся неявно.
А какую вы задачу решаете?
Вот статическая типизация:
foo x = x + 1
Избыточный синтаксис нужен не при статической типизации, а при обязательной декларации типов, но это не обязательно присутствует в статически-типизируемом языке.

Информация

В рейтинге
Не участвует
Откуда
Россия
Дата рождения
Зарегистрирован
Активность