мета-данные страницы
  •  
Загрузка не удалась. Возможно, проблемы с правами доступа?

Различия

Показаны различия между двумя версиями страницы.

Ссылка на это сравнение

Предыдущая версия справа и слеваПредыдущая версия
Следующая версия
Предыдущая версия
haskell [15/09/2018 22:02] – [2.5 Проблемы преобразования типов в выражениях] vlasovhaskell [09/03/2019 20:38] (текущий) – [Урок 8.1 Восходящий Парсер] vlasov
Строка 25: Строка 25:
   - [[http://habrahabr.ru/post/193722/|Haskell в продакте: Отчёт менеджера проекта]]   - [[http://habrahabr.ru/post/193722/|Haskell в продакте: Отчёт менеджера проекта]]
   - [[http://ru-lambda.livejournal.com/3212.html|Haskell: что это такое]]   - [[http://ru-lambda.livejournal.com/3212.html|Haskell: что это такое]]
-  - [[http://dev.by/blogs/main/esli-by-yazyki-programmirovaniya-byli-mashinami|Если бы языки программирования были машинами (шуточное :-))]]+  - [[https://events.dev.by/lenta/main/esli-by-yazyki-programmirovaniya-byli-mashinami|Если бы языки программирования были машинами]], [[https://events.dev.by/lenta/main/esli-by-yazyki-programmirovaniya-byli-religiyami|Если бы языки программирования были религиями]]  (шуточное :-))
   - [[http://anton-k.github.io/ru-haskell-book/book/home.html|Учебник по Haskell. Антон Холомьёв]] (пока лучший учебник на русском!!)   - [[http://anton-k.github.io/ru-haskell-book/book/home.html|Учебник по Haskell. Антон Холомьёв]] (пока лучший учебник на русском!!)
   - [[https://www.ohaskell.guide/|Шевченко Д. О Haskell по-человечески]]   - [[https://www.ohaskell.guide/|Шевченко Д. О Haskell по-человечески]]
Строка 454: Строка 454:
 (везде ниже ''xs'', ''ys'' и т.п. обозначают список) (везде ниже ''xs'', ''ys'' и т.п. обозначают список)
  
-  * ''xs !! n'' --- получим n-й произвольный элемент списка xs, начиная с нулевого; +  * ''xs !! n'' --- получим n-й произвольный элемент списка ''xs'', начиная с нулевого; 
-  * ''head xs'' --- вернет //первый// элемент списка xs; +  * ''head xs'' --- вернет //первый// элемент списка ''xs''
-  * ''last xs'' --- вернет //последний// элемент списка xs; +  * ''last xs'' --- вернет //последний// элемент списка ''xs''
-  * ''tail xs'' --- вернет список xs без //первого// элемента; +  * ''tail xs'' --- вернет список ''xs'' без //первого// элемента; 
-  * ''init xs'' --- вернет список xs без //последнего// элемента;+  * ''init xs'' --- вернет список ''xs'' без //последнего// элемента;
   * ''reverse xs'' --- вернет обратный список;   * ''reverse xs'' --- вернет обратный список;
-  * ''length xs''  --- вернет длину списка xs;+  * ''length xs''  --- вернет длину списка ''xs'';
  
 ==== 3.2 Добавление к списку === ==== 3.2 Добавление к списку ===
Строка 615: Строка 615:
   * ''union xs ys'' -- возвращает объединение двух списков;   * ''union xs ys'' -- возвращает объединение двух списков;
   * ''intersect xs ys'' -- возвращает пересечение двух списков;         * ''intersect xs ys'' -- возвращает пересечение двух списков;      
-  * ''<nowiki>(\\)</nowiki>'' -- возвращает разность (неассоциативную) двух списков, таким образом: ''<nowiki>(xs ++ ys) \\ xs == ys</nowiki>'';+  * ''<nowiki>(\\)</nowiki>'' -- возвращает разность (неассоциативную) двух списков, таким образом: ''<nowiki>(xs ++ ys) \\ xs == ys</nowiki>'' (если нет общих элементов);
   * ''elem x xs'' -- предикат, возвращающий истину, если элемент ''x'' принадлежит списку ''xs'';   * ''elem x xs'' -- предикат, возвращающий истину, если элемент ''x'' принадлежит списку ''xs'';
   * ''tails xs'' -- функция возвращает список хвостов данного списка, напр.:<code haskell>tails "abc" == ["abc", "bc", "c", ""]</code>   * ''tails xs'' -- функция возвращает список хвостов данного списка, напр.:<code haskell>tails "abc" == ["abc", "bc", "c", ""]</code>
Строка 720: Строка 720:
 </code> </code>
  
 +
 +Более детально об импорте модулей можно прочитать тут: [[https://wiki.haskell.org/Import|wiki.haskell: Import]].
 ==== 4.2 Экспорт модулей ==== ==== 4.2 Экспорт модулей ====
  
Строка 1067: Строка 1069:
 (<>) ::  MyAlg -> MyAlg -> MyAlg (<>) ::  MyAlg -> MyAlg -> MyAlg
 O <> x = x O <> x = x
-n <>x = next  (prev n <> x)+n <> x = next  (prev n <> x)
  
 (><) ::  MyAlg -> MyAlg -> MyAlg (><) ::  MyAlg -> MyAlg -> MyAlg
Строка 1177: Строка 1179:
  
  
-**Задание.** Создать собственный класс Logic с операциями &&&, |||, neg --- описывающие сигнатуры и взаимосвязи конъюнкции, дизъюнкции и отрицании. Затем создать тип данных OurBool и воплощения для него класса Logic.+**Задание.** Создать собственный класс Logic с операциями ''&&&,'' ''|||''''neg'' --- описывающие сигнатуры и взаимосвязи конъюнкции, дизъюнкции и отрицании. Затем создать тип данных ''OurBool'' и воплощения для него класса ''Logic''.
  
 Формально класс описывается следующим образом: Формально класс описывается следующим образом:
Строка 1198: Строка 1200:
  
 <code haskell> <code haskell>
-infixl 7 (&&&) +infixl 7 &&& 
-infixl 5 (|||)+infixl 5 |||
 </code> </code>
  
Строка 1274: Строка 1276:
 </code> </code>
  
-Этот код уже не слишком тривиален (что видно по обилию "грозных заголовков"), он был трудный в отладке. Указаны воплощения класса ``Sosedy`` и функции ``(~~)`` для типов ``Int`` и ``Char``. Кроме того, для класса типов ``RealFloat`` (куда входят типы ``Float`` и ``Double``) указано общее воплощение.+Этот код уже не слишком тривиален (что видно по обилию "грозных заголовков"), он был трудный в отладке. Указаны воплощения класса ''Sosedy'' и функции ''(~~)'' для типов ''Int'' и ``Char``. Кроме того, для класса типов ``RealFloat`` (куда входят типы ``Float`` и ``Double``) указано общее воплощение.
  
 Заметим, что функция ``(~~~)`` будет реализована автоматически. Заметим, что функция ``(~~~)`` будет реализована автоматически.
Строка 1294: Строка 1296:
 </code> </code>
  
-Для многострочных программ нам необходимо использовать ключевой слово <nowiki>do</nowiki>, полный смысл которого будет ясен при изучении монад.+Для многострочных программ нам необходимо использовать ключевое слово <nowiki>do</nowiki>, полный смысл которого будет ясен при изучении монад.
  
 Вот как осуществляется получение аргументов командной строки в самом простом случае: Вот как осуществляется получение аргументов командной строки в самом простом случае:
Строка 1334: Строка 1336:
 ==== Урок 6.2 Взаимодействие с STDIN-STDOUT ==== ==== Урок 6.2 Взаимодействие с STDIN-STDOUT ====
  
-Список базовых функций ввода-вывода может быть найден тут: [[http://www.haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#g:24|Basic Input and output]]+Список базовых функций ввода-вывода может быть найден тут: [[https://downloads.haskell.org/~ghc/latest/docs/html/libraries/base-4.12.0.0/Prelude.html#g:25|Basic Input and output]]
 или на русском языке тут: или на русском языке тут:
 [[http://www.haskell.ru/io-13.html|Haskell-98. Основные операции ввода-вывода]]. [[http://www.haskell.ru/io-13.html|Haskell-98. Основные операции ввода-вывода]].
Строка 1545: Строка 1547:
   writeFile "testUp.txt" (unlines up_lst)   writeFile "testUp.txt" (unlines up_lst)
 </code> </code>
-Здесь "чистая функция" transform преобразует в строках символы к верхнему регистру. "Чистая функция" ''lines'' разбивает входящую строку на список строк по признаку конца строки, а функция ''unlines'', наоборот, получив список строк, склеивает их в одну.+Здесь "чистая функция" ''transform'' преобразует в строках символы к верхнему регистру. "Чистая функция" ''lines'' разбивает входящую строку на список строк по признаку конца строки, а функция ''unlines'', наоборот, получив список строк, склеивает их в одну.
  
 Работа с "чистыми функциями" в монадическом коде (для нас пока это означает "внутри блока ''do''") должна осуществляться с помощью конструкции ''let''. Работа с "чистыми функциями" в монадическом коде (для нас пока это означает "внутри блока ''do''") должна осуществляться с помощью конструкции ''let''.
Строка 1552: Строка 1554:
 ==== 6.6 Запуск и компиляция ==== ==== 6.6 Запуск и компиляция ====
  
-Запуск подготовленных указанным выше способом возможен разными путями. +Запуск подготовленных указанным выше способом файлов возможен разными путями. 
 Во-первых, мы можем по-прежнему из ''ghci'' загружать нужный файл и указывать на выполнение функцию ''main''. Во-первых, мы можем по-прежнему из ''ghci'' загружать нужный файл и указывать на выполнение функцию ''main''.
  
Строка 1592: Строка 1594:
  
 <code haskell> <code haskell>
-data Maybe a = Nothing | Just a+data Maybe a = Nothing | Just a deriving (Eq, Ord)
 </code> </code>
 (Напомним, здесь ''Maybe'' --- это конструктор типов, в данном случае полиморфный, параметризованный произвольным типом ''a'', ''Nothing'' и ''Just'' --- конструкторы данных) (Напомним, здесь ''Maybe'' --- это конструктор типов, в данном случае полиморфный, параметризованный произвольным типом ''a'', ''Nothing'' и ''Just'' --- конструкторы данных)
Строка 1602: Строка 1604:
 </code> </code>
  
-Полиморфные типы похожи на контейнеры, которые могут содержать значения многих различных типов. Так, ''Maybe Int'' можно считать контейнером типа ''Maybe'', который содержит ''Int'' тэгом ''Just'' или ''Nothing''.+Полиморфные типы похожи на контейнеры, которые могут содержать значения многих различных типов. Так, ''Maybe Int'' можно считать контейнером типа ''Maybe'', который содержит ''Int'' с тэгом ''Just''или ''Nothing''.
  
 Теперь, предположим, что необходимо написать программу для обслуживания экспериментов по клонированию и скрещиванию овец. Нам потребуются функции ''mother'' и ''father''. Но если овцы клонированы, у них не всегда могут быть и отец, и мать! Теперь, предположим, что необходимо написать программу для обслуживания экспериментов по клонированию и скрещиванию овец. Нам потребуются функции ''mother'' и ''father''. Но если овцы клонированы, у них не всегда могут быть и отец, и мать!
Строка 2605: Строка 2607:
 то не распозналось.. Если элементы во входном списке еще остались, то переходим к шагу 1. то не распозналось.. Если элементы во входном списке еще остались, то переходим к шагу 1.
  
-Ниже применяем полученные функции для создания парсера parser.+Ниже применяем полученные функции для создания парсера ''parse''.
 <code haskell> <code haskell>
 parse teststr = if (mss == "S" parse teststr = if (mss == "S"