Куча говна / Говнокод #12083 Ссылка на оригинал

0

  1. 1
  2. 2
  3. 3
  4. 4
  5. 5
data Trivalent = TriFalse | TriUnknown | TriTrue deriving (Show, Eq, Ord)

(&) :: Trivalent -> Trivalent -> Trivalent -- &&
(!) :: Trivalent -> Trivalent -> Trivalent -- ||
nt :: Trivalent -> Trivalent -- not

В хасскеле нет класса для логических значений. А значит хрен переопределишь операторы &&, || и функцию not

Запостил: Fai Fai, (Updated )

Комментарии (52) RSS

  • (!) зря определил, это индексирование массивов.
    Ответить
        • Значит монадами изучение хаскелла не закончилось... Пойду читать RWH...
          Ответить
          • Именно. Там гигантская библиотека забортом осталась. Одних массивов там несколько штук с разными интрфейсами. А ведь массивы - самая простая структура данных. Так что впереди увлекательный мир нестриженной бороды.
            Ответить
  • Еще один. Ждем-с когда появится Роман а-ля deus ex machina и разъяснит что неосилено топикстартером на этот раз.
    Ответить
      • К слову операторы || и && определяются проще. Если тип Ord и Eq, и False < Unknown < True, то
        x || y = max x y
        x && y = min x y

        Ну а not проще никак не сделать.
        Ответить
    • > что неосилено топикстартером

      А то, что я правильно написал - класса Logical c операторами && || not - нет! Num - есть, Fractional - есть, Integral - есть, Eq, Show, Read, Ord и т.д. и т.п - всё есть.

      А класса для реализации произвольной логики - нет! Есть всего-лишь недотип data Bool...
      Ответить
        • Вот именно за это мне нравятся type classes. Это просто шикарно:
          import Prelude hiding ((&&), (||), not)
          import qualified Prelude
           
          infixr 3  &&
          infixr 2  ||
          infixr 3  `xor`
           
          class Boolean a where
              (&&) :: a -> a -> a
              (||) :: a -> a -> a
              not :: a -> a
           
          data Trivalent = TriFalse | TriUnknown | TriTrue deriving (Show, Eq, Ord)
           
          instance Boolean Trivalent where
              TriFalse && _ = TriFalse
              _ && TriFalse = TriFalse
              TriTrue && TriTrue = TriTrue
              _ && _ = TriUnknown
              TriTrue || _ = TriTrue
              _ || TriTrue = TriTrue
              TriFalse || TriFalse = TriFalse
              _ || _ = TriUnknown
              not TriTrue = TriFalse
              not TriFalse = TriTrue
              not TriUnknown = TriUnknown
           
          instance Boolean Bool where
              (&&) = (Prelude.&&)
              (||) = (Prelude.||)
              not = Prelude.not
           
          xor :: Boolean a => a -> a -> a
          a `xor` b = not a && b || not b && a
           
          main = do
              print $ TriTrue && TriFalse
              print $ not (TriFalse || TriUnknown)
              print $ not (TriUnknown || TriFalse && TriTrue)
              print $ 2 < 3 `xor` False
              print $ map (&& TriTrue) [TriTrue, TriFalse, TriUnknown]
              print $ map (&& True) [True, False]
          Мне остаётся только восхищаться.
          Ответить
          • Тут еще проблема есть. Нельзя использовать операции, принимающие два разных типа из одного тайпкласса. Даже с числами в стандартной библиотеке эта проблема существует. И решается она походу только всякими toXxx да fromXxx
            Ответить
            • Да, такое есть, но на фоне такой же строгой системы типов F#, но без тайпклассов это смотрится просто прекрасно. Хаскель когда решил уровнение с типами - он вывел 10ть нужных тайпклассов для данной переменной и как бы ок. А какой-нибудь F# вывел тебе int и ты уже с ним ничего не сделаешь универсального. Он есть int и все, приехали. В какой нибудь функции ты уже не можешь указать, что тебе нужен лишь интерфейс Eq (в Хаскеле обычно этот Eq сам хаскель выведет). Эта функция в F# должна будет принять конкретно int, а иначе пошлет тебя компилятор. Или опять же ты не можешь написать map f list1. Тебе придется написать List.map f list1. Опять же это из-за того, что нет тайпклассов. Система тайпклассов я считаю гениальна. Эта типизация хаскелю подходит как нельзя лучше.
              Ответить
              • Вообщем в F# настолько ублюдочная типизация, поэтому я считаю, что она не достойна даже, чтобы я на ней писал говно или постил на уютненький говнокод.
                Ответить
                • >она не достойна даже, чтобы я на ней писал говно
                  Какое у тебя самомнение. Лучше вообще не пиши говно, ок?
                  Ответить
                  • >Какое у тебя самомнение.
                    Не. Это мнение о типизации слишком низкое. Рядом есть много более перспективных типизаций, а майкрософт выбрала самую простую и кривую.
                    Ответить
                • 0) Надо же, помнишь.
                  1) В Хаскеле вроде модификация Хиндли-Милнера, в отличие от F#, где он более чистый.
                  2) Я сказал, что эта типизация подходит Хаскелю. Типизация ~= система типов + система вывода типов.
                  Так вот в Хаскеле система вывода типов очень сочитается с системой типов. Очень хорошая подборка связки. Не побоюсь этого слова, очень хороший ученый поработал. Это тот случай когда среди ограничений рождается что-то принципиально новое и сильное.
                  3)Ну да, Немерловый вывод типов много сильнее Хиндле-Милнера за счет того, что система типов .НЕТ используется в полной мере со всеми перегрузками, промоутингом и приведениями типов.

                  То есть вывод типов Хиндле-Милнер становится сильным только из-за правильно инженерно подобранной достаточно простой типизации в Хаскель. F# с Хиндле-Милнером сразу идет лесом, тк типизация используется из .НЕТ, но при этом убого ограниченная и не продуманная (как например в Хаскеле с её классами типов). Ну а в Немерле очень мощный вывод типов, тк работает с типизацией обычного C# без каких либо ограничений или специальной продуманнасти типизации как в Хаскеле. А стандартному Хиндле-Милнеру это и не снилось, что мы и видем на примере F#. Вывод типов F# просто не способен работать с типизацией уровня С#.
                  Ответить
          • З.ы. копипастить мой код было совершенно необязательно. Кому он нужен - прочел бы и на ideone.
            Ответить
            • Ну я боюсь, что идеон стирает старые говнокоды, а так тут может сохранится. :-[
              Ответить
                • Да кстати, надо бы и мне завести учетку. А то клонирую коды десятками, если прямо там пытаюсь пилить.
                  Ответить
                  • Заодно дают возможность делать ограничение по времени 15 секунд.
                    Ответить
          • > Мне остаётся только восхищаться.

            Я сам не понимаю, как мог думать, что интерфейсы и полиморфизм удел объектно-ориентированного программирования.
            А вот те нате - в хаскелле всё это в сто раз элегантнее.

            Я бы сказал в хаскелле всё-всё-всё элегантнее, а монады это лучший способ инкапсуляции состояния.
            Ответить
            • >а монады это лучший способ инкапсуляции состояния.
              А почему вы так считаете? Мне что-то он не слишком понравился. Но надо мне ещё поработать с Хаски, чтобы составить более полное и аргументированное мнение.
              Ответить
              • Просто у меня за множество лет программирования сложилось понятие об идеальном языке программирования (замечу, задолго до того как я даже услышал про хаскелл):

                1. Только строгая статическая типизация.
                2. Никаких неявных преобразований, даже безопасных.
                3. Удобная запись типов.
                4. Удобный синтаксис шаблонов.
                5. Кроссплатформенность.
                6. Надёжность.
                7. Ортогональность. Я ненавижу глупые исключения из правил.
                8. Комбинируемость всех конструкций.
                9. Элегантная и краткая форма записи.

                Как видно Хаскелл подошёл по всем параметрам:
                1. В хаскелле строгая статическая типизация.
                2. В хаскелле нет неявных преобразований.
                3. [a] и (a -> b) намного удобнее чем "std::vector<a>" и "b foo<a>" (сравнение не точное, но суть не меняется).
                4. foo :: a -> a
                5. GHC и Haskell Platform есть под Win, Mac, Lin.
                6. За счёт строгой типизации, автовывода типов и чистоты хаскелл надёжнее чем все эти джавы вместе взятые.
                7. Единственное исключение, найдённое мною в хаскелле - патерн-матчинг не позволяет использовать выражения вроде:
                intsqrt( x^2 ) = x
                8. ВСЁ КОМБИНИРУЕТСЯ. Тоесть вообще всё!
                9. Код на хасскеле короче чем на перле и понятнее чем на питоне!

                Есть только два недостатка, которые меня действительно волнуют - неполноценность типа Bool в стандартной библиотеке (хотя всё это решается) и отсутствие исчерпывающего учебника на русском языке.
                Ответить
                    • Если разберешься с аппликативными функторами, то ответ не заставит себя ждать.
                      http://ideone.com/9LL4Ah
                      Изучай систему типов и стандартную библиотеку. А трибулы (а темболее велосипедные) это костыли.
                      Если конечно, у тебя не чуть ли вся программа на них построена, то конечно и они могут иметь место.
                      Ответить
                • > За счёт строгой типизации, автовывода типов и чистоты хаскелл надёжнее чем все эти джавы вместе взятые.
                  Столкнешься с ленивым вводом-выводом, еще вспомнишь свои слова о надежности.

                  > Код на хасскеле короче чем на перле и понятнее чем на питоне!
                  А вот тут неправда. Функциональный код то короче, но когда пытаешься писать императивщину - то длиннее, и отступы быстро наматываются.
                  Ответить
                • 2, 5 - это реализация, а не язык: поскольку говорится о "идеале", то эти сущности стоит разделять

                  > 2. В хаскелле нет неявных преобразований.
                  что вы понимаете под ними, а то в том же ghc есть rewrite-rules

                  > 5. GHC и Haskell Platform есть под Win, Mac, Lin.
                  есть и аппаратная сторона, с тем же армом еще проблемы

                  > 7. Единственное исключение...
                  это уже вне сопоставления по образцу, а скорее в сторону пролога

                  > 9. Код на хасскеле короче чем на перле и понятнее чем на питоне!
                  очень спорно

                  > Есть только два недостатка, которые меня действительно волнуют...
                  "i have bad news for you", скорее это высокии барьер (что, впрочем, проблема экосиситемы, а не языка); сложно предсказуемая эффективность: незначительные изменения в коде могут кардинально влиять на производительность, нехватку или избыточность ленивости довольно тдудно выловить
                  Ответить
              • Ещё добавлю, что до хаскелла почётное первое место занимал питон, который подходит по большей части пунктов (но не по всем).

                Реальный код всё-равно приходится писать на си/плюсах/ас3/жабе...
                Ответить
                • > Реальный код всё-равно приходится писать на си/плюсах/ас3/жабе...
                  PHP...
                  Ответить
              • Я вот начинаю думать, что вы правы и ситуация довольно близка. Я поэксперементировал (хотя надо бы ещё). Похоже typeclasses не содержит виртуальных функций. Например функции принимающие "тип_класса тип => конструктор_типа тип" похоже принимают эту функцию не как интерфейс с виртуальными функциями, а как шаблон (из крестов) с ограничениями (where в генериках C#). То есть это все вполне может работать очень оптимизированно. Наверное благодаря этому Хаскель такой быстрый. Виртуальные функции похоже появляются только после применения предиката форол: "forall тип. тип_класса тип => конструктор_типа тип". Надо конечно над всем этим ещё поразмышлять, но похоже все именно так.
                Ответить
                • Наверное благодаря этому Хаскель такой быстрый *.
                  * По сравнению с python и javascript
                  Ответить
                  • Хаскель традиционно раза в 2-3 медленее сишечки. Имхо очень круто для очень высокоуровнего языка.
                    Ответить
                    • Хаскель* традиционно раза в 2-3 медленее сишечки**.

                      * Если программист опытный.
                      ** Если программист нуб или оптимизация по времени не требовалась.
                      Ответить
                • *Например функции принимающие параметер типа "тип_класса тип => конструктор_типа тип" похоже принимают этот параметер не как интерфейс с виртуальными функциями, а как шаблон (из крестов) с ограничениями (where в генериках C#).
                  selfix ночных посиделок
                  Ответить
  • И ещё не забудь добавить вероятностный (не чёткий) булеан.
    Ответить

Добавить комментарий

Семь раз отмерь — один отрежь, guest!

    А не использовать ли нам bbcode?


    8