Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

parts of translation and editing questions #106

Open
wants to merge 12 commits into
base: master
Choose a base branch
from
131 changes: 73 additions & 58 deletions drafts/2018-01-18-effects-haskell.en.md
Original file line number Diff line number Diff line change
@@ -1,33 +1,29 @@
---
author: Юрий Сыровецкий
title: Эффекты в Haskell
tags: эффекты
title: Effects in Haskell
tags: effects, purity
description: Effects implementation in Haskell.
---

Draft translation into English.
In this article we will demonstrate that procedures (functions with effects)
do not require special support from the programming language and that
regular "pure" functions can be used to handle these procedures with effects.
cblp marked this conversation as resolved.
Show resolved Hide resolved

Сегодня мы докажем, что для процедур,
то есть «функций с эффектами» не нужна особая поддержка со стороны языка
программирования,
достаточно реализации обычных «чистых» функций.
As an example we will use Haskell, a pure functions language, which does not have the embedded effects in a way "impure" C, OCaml, JavaScript do.
However, we can build pure, controllable effects in Haskell, which
serve our goals quite similarly as "impure" effects.

Для примера возьмём Haskell — чистый язык, в котором, в отличие от «нечистых» C,
OCaml, JavaScript и прочих, нет никаких встроенных эффектов.
(Ну, почти нет.)
Однако, средствами этого языка можно построить чистые управляемые эффекты,
и не хуже, чем «нечистые».

---
<!--

Make a footnote:

---
В [предыдущей статье](../10/effects.html) мы познакомились с основными видами эффектов в математике и программировании.

-->

В [предыдущей статье](../10/effects.html) мы познакомились с основными видами
эффектов в математике и программировании.

---
<!-- Понимаю, знаю как перевести -->

_Замечание о терминах._
Я позволю себе называть параметрические типы с опущенными параметрами просто
Expand All @@ -42,13 +38,13 @@ _типами_,
а если по контексту подразумевается всё-таки конкретный тип,
значит, речь идёт о конструкторе с произвольными значениями параметров.

## 0. No effects -- Отсутствие эффектов
## 0. No effects

Представим чистую функцию `f :: a -> b` в виде чёрного ящика:
We can represent a pure funciton `f :: a -> b` as a black box that takes in a value of type `a` and returns a value of type `b`:

<center>![](../../../../../files/posts/2018-01-18/pure.svg)</center>

## 1. Эффект частичности
## 1. Partiality effect

<center>![](../../../../../files/posts/2018-01-18/partial.svg)</center>

Expand All @@ -60,10 +56,10 @@ data Maybe a = Nothing | Just a
```

Value of type `Maybe a` either contains a value
of type `a`, or there is no such value.
of type `a`, or there is no value.

We can describe a partial procedure that optionally
returns type `b`, as a function that always returns `Maybe b`.
returns type `b` as a function that always returns `Maybe b` type.

<center>![](../../../../../files/posts/2018-01-18/partial-pure.svg)</center>

Expand All @@ -79,17 +75,14 @@ headM [] = Nothing -- cannot take a head of empty list
headM (x:_) = Just x -- head of non-mepty list - here it is!
```

Please note, that `Maybe` type belongs to `Functor`, `Applicative`,
Please note that `Maybe` type belongs to `Functor`, `Applicative`,
`Monad` and other interesting and useful typeclasses.

In practice we can also use `Either` and `Except`,
implementing similar effect as `Maybe`, but
allows to add additional information why
a computation was not completed.
In practice we can also use `Either` and `Except` types. They
implement similar effect as `Maybe`, but
also add additional information why a computation was not completed.

<! -- Пример -->

In example below we introduce an error type
In example below we introduce an error data type
`MyError` with a sole value `EmptyList`.
`MyError` will be used in other code examples below.

Expand All @@ -100,80 +93,102 @@ data Either a b

data MyError = EmptyList -- denotes an custom error name


headE :: [a] -> Either MyError a
headE [] = Left EmptyList
headE (x:_) = Right x
```

<!-- Тут бабах MonadError, когда читатель ни сном ни духом. -->
<!-- Тут бабах MonadError, когда читатель ни сном ни духом.
Может как-то подготовить, о том, что о будет дальше?-->

Можно комбинировать частичность с другими эффектами:
Partiality can be combined with other effects. Below we use
`MonadError` from [mtl](https://hackage.haskell.org/package/mtl-2.2.2/docs/Control-Monad-Except.html) package for exception processing:

```haskell
headE
:: MonadError MyError m -- 'm' поддерживает эффект "ошибки"
:: MonadError MyError m -- 'm' type constructor supports "error" effects
=> [a] -> m a
headE (x:_) = pure x
headE [] =
throwError EmptyList -- эффект ошибки, прекращение дальнейших вычислений
throwError EmptyList -- we add an error effect, it terminates further computations
```

Partiallity is the only effect that can arise from inside Haskell.
The rest of the effects require some act of the outside world, while
partiality situation can be constructed by means of Haskell itself
as we show in examples below.

<!--

На самом деле частичность — единственный неуправляемый эффект,
доступный в Хаскеле непосредственно.

<!-- EP: доступно непонятно - кому? Доступно - ожидаение
читателя, что про что-то хорошее сейчас скажут, а тут о
EP: доступно непонятно - кому? После "Доступно" читатель
ждет, что про что-то хорошее сейчас скажут, а тут о
зависании внутри цикла.

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

Partiallity is the only incontrollable effect that can
arise from "inside" Haskell by using the contructs of
the language itself. All other effects are produced
by outside world.

-->


<!--
Любая функция может оказаться частичной,
то есть зависнуть или выбросить исключение,
по ошибке или из-за несовершенства реального мира.

<!-- EP: Тут что-то нелогичное с позиций чистых функци - им-то какое

EP: Тут что-то нелогичное с позиций чистых функци - им-то какое
дело до несовершенства реального мира?
-->

Going into an infinte loop is one of partiality effect:


```haskell
-- простейший бесконечный цикл
x = x -- вычисление 'x' приводит к вычислению 'x', снова и снова

-- не столь тривиальный пример зависания
-- a simplistic infinite loop
x = x -- computation of 'x' requires 'x' again and again

-- a slightly longer example:
-- takeWhile (< 10) will require a value 10 or above
-- to stop, there will be no such value in
-- [2, 1 ..], so length of infinite list
-- will never be computed
n = length $ takeWhile (< 10) [2, 1 ..]
```

К сожалению, в полных по Тьюрингу языках этого невозможно избежать,
полнота влечёт возможность реализации бесконечного цикла,
то есть незавершения программы.
Существуют языки, не полные по Тьюрингу,
и на них тоже можно писать сколь угодно сложные программы без эффекта
частичности,
то есть гарантированно тотальные,
но такое требование существенно усложняет язык.

К счастью, в Хаскеле доступна управляемая частичность,
и иметь дело с неуправляемой частичностью приходится редко.
<!-- Понимаю, знаю как перевести -->

In Turing-complete languages the possibility of an infinite loop
cannot be avoided. There are non-Turing-complete programming
languages, where the programs will avoid partiality effect
and the program 'totality' is be garanteed, but the drawback
is an increase in langauge complexity. [This link](https://stackoverflow.com/questions/315340/practical-non-turing-complete-languages) provides a discussion of several non-Turing-complete languages
with respect to program termination guarantee.

Luckily in Haskell we can use controlled partiallity and
cases of uncontrolled partiallity are rather rare.

## 2. Эффекты недетерменированности (неопределённости)
## 2. Indeterminism (uncertainty) effect

### 2.1. Эффект нестабильности
### 2.1. Instability effect

<center>![](../../../../../files/posts/2018-01-18/unstable.svg)</center>

Если процедура для одного и того же значения аргумента может вернуть от раза
к разу разные результаты,
это значит, что на самом деле результат зависит от чего-то ещё.

Даже генератор случайных чисел (настоящий, аппаратный) — это «чистая» функция,
зависящая от состояния источника энтропии.
Даже генератор случайных чисел (настоящий, аппаратный) — это «чистая» функция, зависящая от состояния источника энтропии.

Чтобы представить этот эффект чистой функцией,
надо всего лишь неявную зависимость сделать явной.
Expand Down