Различия

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

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

Предыдущая версия справа и слева Предыдущая версия
Следующая версия
Предыдущая версия
Следующая версия Следующая версия справа и слева
haskell [15/09/2018 22:01]
vlasov [2.5 Проблемы преобразования типов в выражениях]
haskell [25/11/2018 17:17]
vlasov [6.5 Работа с файлами]
Строка 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 по-человечески]]
Строка 384: Строка 384:
  
 <​note>​ <​note>​
-Как показали дальнейшие изыскания,​ изначальное поведение было обусловлено ещё одной проблемой Haskell, так называемом ограничении мономорфизма:​+Как показали дальнейшие изыскания,​ изначальное поведение было обусловлено ещё одной проблемой Haskell, так называемом ​//ограничением мономорфизма//:
 [[https://​wiki.haskell.org/​Monomorphism_restriction|Monomorphism_restriction]]. В современных версиях ghci это ограничение отключено,​ но при желании его можно вновь включить и потестировать указанные выше странности:​ [[https://​wiki.haskell.org/​Monomorphism_restriction|Monomorphism_restriction]]. В современных версиях ghci это ограничение отключено,​ но при желании его можно вновь включить и потестировать указанные выше странности:​
 <​code>​ <​code>​
-Some flags have not been recognized: -X 
 Prelude> :set -XMonomorphismRestriction Prelude> :set -XMonomorphismRestriction
 Prelude> let x = 2 Prelude> let x = 2
Строка 400: Строка 399:
  
  
-Вот версия более простого и понятного примера:​+Вот версия более простого и понятного примера, без странностей ограничения мономорфизма:
  
 <code haskell> <code haskell>
Строка 411: Строка 410:
       In an equation for `it': it = x + y       In an equation for `it': it = x + y
 </​code>​ </​code>​
-В языках типа Си это соответствовало бы объявлению и инициализации переменных типа ​Int и Double, а потом совместного их использования в одном арифметическом выражении.+В языках типа Си это соответствовало бы объявлению и инициализации переменных типа ​int и double, а потом совместного их использования в одном арифметическом выражении.
 ==== 2.6 Использование монады состояния==== ==== 2.6 Использование монады состояния====
  
Строка 455: Строка 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 Добавление к списку ===
Строка 616: Строка 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>​
Строка 721: Строка 720:
 </​code>​ </​code>​
  
 +
 +Более детально об импорте модулей можно прочитать тут: [[https://​wiki.haskell.org/​Import|wiki.haskell:​ Import]].
 ==== 4.2 Экспорт модулей ==== ==== 4.2 Экспорт модулей ====
  
Строка 1068: Строка 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
Строка 1178: Строка 1179:
  
  
-**Задание.** Создать собственный класс Logic с операциями &&&,​ |||, neg --- описывающие сигнатуры и взаимосвязи конъюнкции,​ дизъюнкции и отрицании. Затем создать тип данных OurBool и воплощения для него класса Logic.+**Задание.** Создать собственный класс Logic с операциями ​''​&&&,​''​ ''​|||''​''​neg'' ​--- описывающие сигнатуры и взаимосвязи конъюнкции,​ дизъюнкции и отрицании. Затем создать тип данных ​''​OurBool'' ​и воплощения для него класса ​''​Logic''​.
  
 Формально класс описывается следующим образом:​ Формально класс описывается следующим образом:​
Строка 1275: Строка 1276:
 </​code>​ </​code>​
  
-Этот код уже не слишком тривиален (что видно по обилию "​грозных заголовков"​),​ он был трудный в отладке. Указаны воплощения класса ​``Sosedy`` и функции ​``(~~)`` для типов ​``Int`` и ``Char``. Кроме того, для класса типов ``RealFloat`` (куда входят типы ``Float`` и ``Double``) указано общее воплощение.+Этот код уже не слишком тривиален (что видно по обилию "​грозных заголовков"​),​ он был трудный в отладке. Указаны воплощения класса ​''​Sosedy'' ​и функции ​''​(~~)'' ​для типов ​''​Int'' ​и ``Char``. Кроме того, для класса типов ``RealFloat`` (куда входят типы ``Float`` и ``Double``) указано общее воплощение.
  
 Заметим,​ что функция ``(~~~)`` будет реализована автоматически. Заметим,​ что функция ``(~~~)`` будет реализована автоматически.
Строка 1295: Строка 1296:
 </​code>​ </​code>​
  
-Для многострочных программ нам необходимо использовать ключевой слово <​nowiki>​do</​nowiki>,​ полный смысл которого будет ясен при изучении монад.+Для многострочных программ нам необходимо использовать ключевое слово <​nowiki>​do</​nowiki>,​ полный смысл которого будет ясен при изучении монад.
  
 Вот как осуществляется получение аргументов командной строки в самом простом случае:​ Вот как осуществляется получение аргументов командной строки в самом простом случае:​
Строка 1335: Строка 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. Основные операции ввода-вывода]].
Строка 1546: Строка 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''​.
Строка 1553: Строка 1554:
 ==== 6.6 Запуск и компиляция ==== ==== 6.6 Запуск и компиляция ====
  
-Запуск подготовленных указанным выше способом возможен разными путями. ​+Запуск подготовленных указанным выше способом ​файлов ​возможен разными путями. ​
 Во-первых,​ мы можем по-прежнему из ''​ghci''​ загружать нужный файл и указывать на выполнение функцию ''​main''​. Во-первых,​ мы можем по-прежнему из ''​ghci''​ загружать нужный файл и указывать на выполнение функцию ''​main''​.
  
Строка 1593: Строка 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''​ --- конструкторы данных)
Строка 1603: Строка 1604:
 </​code>​ </​code>​
  
-Полиморфные типы похожи на контейнеры,​ которые могут содержать значения многих различных типов. Так, ''​Maybe Int''​ можно считать контейнером типа ''​Maybe'',​ который содержит ''​Int''​ тэгом ''​Just''​ или ''​Nothing''​.+Полиморфные типы похожи на контейнеры,​ которые могут содержать значения многих различных типов. Так, ''​Maybe Int''​ можно считать контейнером типа ''​Maybe'',​ который содержит ''​Int'' ​с тэгом ''​Just''​или ''​Nothing''​.
  
 Теперь,​ предположим,​ что необходимо написать программу для обслуживания экспериментов по клонированию и скрещиванию овец. Нам потребуются функции ''​mother''​ и ''​father''​. Но если овцы клонированы,​ у них не всегда могут быть и отец, и мать! Теперь,​ предположим,​ что необходимо написать программу для обслуживания экспериментов по клонированию и скрещиванию овец. Нам потребуются функции ''​mother''​ и ''​father''​. Но если овцы клонированы,​ у них не всегда могут быть и отец, и мать!
haskell.txt · Последние изменения: 09/03/2019 20:38 — vlasov
CC Attribution-Noncommercial 4.0 International
Driven by DokuWiki Recent changes RSS feed Valid CSS Valid XHTML 1.0