Как составлять монады State и IO - PullRequest
3 голосов
/ 15 июня 2019

В игре Connect4:

  • мы начинаем с пустой сетки
  • два игрока кладут фигуры х и о на сетку
  • выигрывает первый игрок, набравший 4 фигуры подряд!
  • это текстовая консольная игра

Я думаю, что:

  • на каждом этапе игры Сетка переходит из одного состояния в другое
  • следовательно мне нужно использовать Государственную монаду
  • и потому что это консольное приложение, включающее io
  • в этом случае мне также нужно использовать монаду IO

Правильно ли это мышление?

Предполагая, что вышеприведенное верно, какой из них правильный?

  • Тип StateInIO [S, A] = IO [Состояние [S, A]]
  • тип IOInState [S, A] = состояние [S, IO [A]]

Я предпочитаю второй вариант, имеет больше смысла для меня.

Можно ли сложить эти монады (State, IO) таким образом?

Ответы [ 2 ]

2 голосов
/ 16 июня 2019

State у кошек фактически определяется как псевдоним типа для преобразователя монад StateT[F[_], S, A], где F[_] - тип эффекта. Этот псевдоним исправляет F[_] с Eval, поэтому выглядит как type State[S, A] = StateT[Eval, S, A]. В вашем случае вы должны просто определить свое собственное состояние ввода-вывода, например type IOState[S, A] = StateT[IO, S, A].

StateT[IO, S, A] соответствует IO[S => IO[(S, A)]], и я чувствую, что это более полезный стек, потому что теперь вы можете легко соединить код, используя этот стек, с остальной частью вашего приложения, используя IO.

Вы можете найти больше информации о монаде состояния стека с монадой эффектов с StateT в разделе эффектов чередования в документации State от кошек.

1 голос
/ 15 июня 2019

Я думаю, вы должны просто написать работающую программу и впоследствии обобщить / реорганизовать ее, вместо того, чтобы перегружать ее заранее.Вам нужно State[S, A] для бизнес-логики и IO[A] для взаимодействия с консолью.Но вам не нужно смешивать это.

Тогда в основном классе, где вы пишете цикл взаимодействия с пользователем, вы можете использовать StateT, который объединяет оба ваших типа.

Поway IO[State[S,A]] не выглядит как очень полезный тип.Он говорит, что вы можете прочитать State[S, A] из реального мира.State - это функция.Нет никаких разумных способов прочитать функцию из реального мира.Так что, скорее всего, вам нужно что-то менее мощное.Конечно, этот тип имеет смысл в контексте монадных трансформаторов.

...