Pull to refresh

Comments 4

С многим согласен, но с тем, чтобы шире использовать элементы функционального программирования в C# — не согласен. Потому что это порождает явление, которое я называю функциональщиной: использование элементов и подходов ФП без ограничений, присущих ФП.
Например, ничтоже сумящеся, запихнуть в композицию функцию с побочным эффектом.
Характерный пример — код инициализации ASP.NET Core в шаблоне Generic Host, обеспечивающий совместимость со старыми модулями, написанными под шаблон Web Host.
У интерфейсов построителей (IHostBuilder/IWebHostBuilder) в этих шаблонах есть ряд методов (ConfigureServices и т.п.), которые по выполняемым функциям эквивалентны — они добавляют в очередь на конфигурирование соответствующего компонента делегаты, которые это самое конфигурирование производят, но сигнатуры этих делегатов немного отличаются: делегаты для Generic Host принимают как параметр объект контекста типа HostBuilderContext, а соместимые с Web Host — WebHostBuilderContext. Поэтому было принято совершенно логичное решение — класс, который реализует IWebHostBuilder в Generic Host, помещает в очередь конфигурирования Generic Host композицию из вызова метода, преобразующего один контекст в другой — GetWebHostBuilderContext и вызова исходного делегата.
Все было бы хорошо, но разработчик, писавший GetWebHostBuilderContext, нагрузил его кучей побочных эффектов: он не только кэширует созданный объект WebHostBuilderContext (ну, типа чтобы два раза не вставать) внутри входного параметра (и не делает «лишней работы» если запись в кэше уже есть), но ещё и создает и отправляет в тот же кэш дополнительный объект типизированных параметров веб-приложения WebHostOptions (откуда, кстати, его некоторые методы потом достают). Ну и как вишенка на тортике, он может и поменять ранее закэшированный объект WebHostBuilderContext (во время имнициализации в HostBuilderContext меняется ссылка на объект конфигурации — с минимальной «конфигурации хоста» на полную «конфигурацию приложения», и это изменение записывается в закэшированную копию WebHostBuilderContext).
Я не знаю, какой кровью MS справилась с отлавливанием багов в эттом дивном коде (но, судя по тому, что ASP.NET работает более-менее ровно — таки справилась), но быть участником такого процесса разработки я явно не хочу. Не говоря уж о том, что читать такой код впоследствии, мягко говоря, сложно.
Именно поэтому я за то, что в языках общего назначния типа C# элементы ФП либо должны отсутствовать, либо чтобы копилятор принуждал использующих эти элементы соблюдать предумотренные подходом ФП ограничения.
ФП без ограничений, присущих ФП

Если в одном месте кто-то допустил ошибку в архитектуре, это не значит, что нужно выкидывать на помойку целый пласт инструментов.
Мне вот очень зашли приемы ФП в C#. Да, можно выстрелить в ногу при неправильном использовании, но гибкость нивелирует большинство рисков.
Применяя приемы ФП мы делаем огромнейший шаг для поддержки распараллеливания кода, что обычным ООП — достаточно трудно добиться.

Я некоторое время назад, когда изучал различия функционального подхода и ООП тоже FizzBuzz в качестве "подопытного проекта" использовал))) Вышло, конечно, далеко не так, как в статье, да и делал я исключительно на C#, но всё равно опыт был интересный)
Кому любопытен мой вариант, оставлю ссылочку на репку.

Sign up to leave a comment.