Сергей Самойленко @samsergey
Руководитель, научный сотрудник, преподаватель
Information
- Rating
- Does not participate
- Location
- Петропавловск-Камчатский, Камчатский край, Россия
- Date of birth
- Registered
- Activity
Руководитель, научный сотрудник, преподаватель
Есть, компилятор не пропустит.
Бедная сова. Дело в том, что кто-то определился с определениями, в частности, понятия "эффект" и работает с ним, понимая что и зачем делает. А кто-то спорит о словах и применяет "совиную" аргументацию.
Замените "эффект" на "контекст", может быть, это поможет понять, зачем это нужно. Но главное — если вам монады не нужны, не ссорьтесь, а просто не используйте их.
А если стоит задача доказать? В чем же тут неконструктивность? Доказательство один из способов верификации решения. Или тестирование и охрана ассертами это тоже неконструктивно?
Кто-то пишет библиотеки и возится с О-большими, корректностью, верификацией и прочим "матаном", а кто-то их комбинирует, не задумываясь, а считая, что "это уже сделано".
Или так: попробовал, понял область применения и применяешь, если нужно. Многим нужно.
Не всё. Монады не про ввод/вывод, а про композицию в контексте. Одним из контекстов может быть "внешний мир", но их гораздо больше: неоднозначные вычисления, вероятностные вычисления, параллельность и корутины… При этом синтаксически одна программа может выаолняться в разных контекстах. Это как ортогональные криволинейные координаты: один раз выразил дифференциальные операторы в терминах чисел Ламе и получаешь один и тот же дифур, но в разных контестах.
Можно подходить к этому так. Программа с IO это чистая функция — рецепт того, что делать при конкретных входах. После чего мы подаём ей на вход разные варианты внешнего мира так же, как в интерпретаторе функции plus подаём разные числа. При этом, концептуально, одинаковым мирам всегда соответствует одинаковый ответ. getLine, в мире, в котором клавиатура всегда возвращает "123", всегда вернёт "123". миров много, но и у функции plus возможно много входных параметров.
Не воспринимайте IO-функции как нечто инородное в чистом ФП, а монады требуются не для обеспечения чистоты, с этим проблем нет, а для обеспечения порядка вычислений в ленивом языке.
Грубовато вышло… вызывает желание ответить тем же.
Можно так:
Как видите, программа вполне соответствует тому, что она делает (хоть и монады).
Но если бизнес-логика становится сложнее, её лучше выделить в чистую функцию, а ввод-вывод скомпоновать отдельным блоком. Например, как-то так:
После семи лет ежедневной и плотной работы в Wolfram Mathematica, мне её показалось мало и в моём инструментарии появился Lisp. Ещё через пять лет мне стало тесно и в нём, так я пришёл к Хаскелю, Axiom, Agda, поскольку в них математическая мысль формулируется точнее и строже. И всё это прекрасно сочетается в работе и не мешает писать для развлечения на JavaScript :) Или вы предлагаете отменить все прочие языки, оставив лишь те, что нравятся вам?
Зачем выращивать рис, когда есть макароны? Зачем снимать кино, когда есть книги? Зачем переусложнять и говорить по-китайски, когда есть понятный и простой румынский? Ответ прост: потому что можно. Так развивается человечество.
За что, простите?
Мы видели появление и исчезновение панков, металлюг, эмо, готов, скинов и прочих и прочих… и это пройдёт. Однако прошу обратить внимание, что хипстеры а) не деструктивны и не агрессивны, скорее, наоборот за здоровый образ жизни и работы, б) очевидный консюмеризм метросексуалов существенно дополняют творческой составляющей, в) способствуют популяризации знания технологий и их развитию. Оппозиция не основный их флаг. И я бы сказал, что они в оппозиции к массовому потребительству, агрессии, "страданий по задолбавшей работе", "долгожданной пьяной пятницы", "трёпу в курилке", "кайфу в подъезде" и "романтике грибных трипов" и прочим деструктивным атрибутам. На фоне того, что появлялось с 70-х до 2000-х это вовсе неплохо. По студентам вижу, что внешние признаки принадлежности к этой субкультуре соответствуют определённому внутреннему содержанию, которое помогает им и в учёбе и в работе. А смузи, молескины и Kotlin… ну, я люблю Emacs, кофе и галстуки, что не говорит обо мне ровным счётом ничего, а то что математически ёмкие технологии становятся модными меня радует. Забавно, что существует оппозиция хипстерам, всерьёз неприемлющая смузи :)
Не только, ещё нужно сказать о том, что "Данная работа не опирается на ложные выводы современной науки." А после, посчитав количество минусов, видимо, полагается объявить о том, что новый взгляд на Мир зажимается "официальной наукой".
По-моему, это вполне себе решение в духе Пеано. Это первое что пришло в голову.
Выводы в статье делаются правильные, и тема связи семантики, типов и дуальности, сама по себе, очень интересная. Но не покидает ощущение, что примеры на Haskell немного не в тему. Всё-таки, рассматриваемые паттерны существенно опираются на побочные эффекты и изменение состояния. Синтаксис Haskell очень хорош, не спорю, он и создавался для подобных рассуждений, но с точки зрения семантики, он тут ни при чём. В рамках чистого функционального программирования, приводимые типы либо населены крайне скудно и тривиально, либо, как в случае с
() -> t
, и вовсе соответствуютVoid
. Возможно, лучше было бы ограничиться формальными математическими обозначениями или диаграммами.Совершенно не понравилось. А как же про сохранение математической структуры?
В ваших комментариях очень много личного: "я заворачиваю", "надавать по ушам", "у меня не пройдет ревью"… это имеет отношение к статье, к аппликативным функторам, к парсингу? Вышел долгий спор о привычках и вкусах, не несущий ничего нового, свежего, интересного.
Мне кажется, вы прицепились к самому простому, тривиальному и неинтересному вопросу в программировании. Дискуссия вышла длинная, но с контексте статьи и CS ни о чем. Столько же времени и слов можно было бы потратить на что-либо другое.
Тут две строчки. Всего две короткие симметричные строчки, все обозначения определены тут же. Типы объясняют что делает функция, компилятор подтверждает, что реализация верна. Да, нужно остановиться ненадолго, но с этим можно разобраться, и этот опыт будет полезен. И это не APL, не J в двух строчках на которых можно сломать ногу, здесь из абстракций только генерация списка.
Затем, чтобы разобраться, что происходит. Проще всего использовать
derive Functor
, он выводится однозначно. StateT это верное решение, но не для туториала, придется слишком много тащить лишней инфраструктуры. Бесточечное определение, может быть, и выглядит колдовством, но оно отражает смысл преобразования: разворачиваем, заходим в "на дно" функтора, он у нас трехуровневый, и заворачиваем. При этом становится видно, что мы не делаем ничего лишнего.