Как стать автором
Обновить

Комментарии 143

Та же история — C#, энтерпрайз, клин код, абстрактные фабрики синглтонов, вера в Фаулера, мрак, безысходность.


F# открыл для меня другой мир. Мир где всё логично (как матан) и просто (как LISP), но тем не менее функционально (во всех смыслах) и практично. И денег ещё за это платят больше чем за страдания на C#.


Чем ещё хорош F# — это практичный язык, который не претендует на звание чистого, как Хаскель. В нём можно наговнокодить как в C#! И ещё он примазался к одной из крупшейних экосистем — .Net, что сразу снимает кучу головняка, интеграции, SDK, драйвера, БД, ОРМы и пр. Azure и Visual Studio идут в придачу (мало кто из ФП языков может похвастаться поддержкой таких IDE и облака).


Но есть и минусы, самый большой связан с C# :) Он (C#) настолько хорош, то убедить бизнесы переходить с него — прям таки адски сложная задача. Стоит ли? Вопрос не праздный, ответа у меня нет, я-то уже перешёл и не испытываю проблем с поиском работы.
А вот существующему бизнесу на C# вряд ли оправдано бросаться в пучины F#.

> И денег ещё за это платят больше чем за страдания на C#.

Вот кстати очень редко вижу вакансии на F#, они вообще существуют в достаточном объеме?
Вот кстати очень редко вижу вакансии на F#, они вообще существуют в достаточном объеме?

Меня это немного смущало когда я на HH.ru не нашёл (2017) ни одной вакансии на F#, но резюме выложил. А звонки-то пошли! Из известных компаний где есть F# в РФ — Касперский и Microsoft. Звонили иногда из соображений — "F#? really?". Знающие работодатели хотели меня видеть у себя на C# позициях, но за бОльшие деньги. В итоге я нашёл себе работу на чистом F#, хотя ни одной F# вакансии в РФ на HH.ru на тот момент не было.

Ваше резюме было заточено именно на F#-вакансии? Или в нем был также указан C# и сопутствующие технологии?
Ваше резюме было заточено именно на F#-вакансии? Или в нем был также указан C# и сопутствующие технологии?

Никакой заточки, просто перечислил что знаю. У F# те же технологии.
Но указано было F#/C# Developer, да.

А может есть какой-то транслятор F# => C#? Пишешь на F#, а на работу отдаёшь что требуют, понятно что иногда он возможно будет странно выглядеть, но всё же.
А может есть какой-то транслятор F# => C#?

dotPeek :) Но качество трансляции не очень!

надо улучшать! :)
А вот недавно обсуждали в одном чатике такую задачу: транслировать код из одного высокоуровневого языка в другой, при этом генерируя максимально идеоматичный результат. Дак вот, в общем случае это красиво сделать нельзя, всегда будут костыли и допущения, а F# и C# как раз сильно отличаются. Увы!

Интересно, что внутри там одинаковый IL.
Рихтер в своей небезызвестной книге топит за то, что следует в одном проекте использовать разные языки по мере надобности и от этого одни плюсы.

С одной стороны да.

С другой если есть кусок, написанный «Ф шарпистом», которого никто в команде не понимает, то автобусный коэффициент возрастает очень существенно.

Не считая времени на хлоивары «C# vs F#» на кухне, и различные взгляды на решение проблем «функциональный vs AdapterFacadeFactoryObserber»
Тут есть, иногда работает: github.com/jindraivanek/cs2fs.
Но вообще не надо таким заниматься — чтобы поймать F# надо думать как F#! :) А этот тул, например, переводит один к одному, когда в F# есть много штук, которые делают тоже самое, но короче, надёжнее, читабельнее, итп.

Нет, я так понял, речь об обратном шаге — писать "короче, надёжнее и читабельнее", а потом сконвертировать, чтобы начальство схавало.

Но есть и минусы, самый большой связан с C# :) Он (C#) настолько хорош, то убедить бизнесы переходить с него — прям таки адски сложная задача. Стоит ли?

Долго для самого себя искал аргументы, чтобы перейти с C# на F# в продакшн, но не нашел достаточного количества. Какие факторы стали решающими для вас?

Удачно опробовал F# на проекте с Akka.Net, но дальше меня внедрение языка не ушло)
Я не хотел полумер и стал целенаправленно искать работу на F#.
Оказалось что ее достаточно даже в РФ)


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


А вот захантить таких людей надо обязательно в любой проект на C#, они подтянут уровень кода и команды.


Я сейчас работаю в компании, которая начинала на F#. Думаю это единственный возможный вариант встретить энтерпрайз на этом языке.

Чем ещё хорош F# — это практичный язык, который не претендует на звание чистого, как Хаскель.

Но чистота очень даже практична. "Не практична" у хаскеля как раз сырая экосистема. Как язык хаскель всё же куда проще, понятнее и практичнее чем его "аналоги" из JVM и .Net мира.


Вон те же линзы, которые изобрели в хаскеле, ИМХО, самое практичное, что есть в программировании. На втором месте в моём топе практичности монады + tagless final, которые очень упрощают тестирование и переиспользование кода. Ленивость тоже практичная штука с точки зрения "писать декларативный код и заранее не париться об оптимизации".

Но монады не изобретение и не эксклюзив хаскеля. Как и таглесс. Как и линзы (которые вообще-то костыль для изменения вложенных иммутабельных структур, а никак не лучшее изобретение).


Линзы и монады есть и в F#. В виду отсутствия HKT это просто чуть менее удобно, но это с лихвой окупается экосистемой.


Нет, хаскель хорош. Для обучения тому самому ФП, голову сломать, мышление поменять. Работать на нём — нет спасибо, у меня семья)

которые вообще-то костыль для изменения вложенных иммутабельных структур, а никак не лучшее изобретение

Линзы это не костыль а first-class аксессоры (на самом деле линзы это даже более общая штука), которые покрывают куда более широкий спектр задач. Например линзами можно удобно разбирать сложные JSON и XML, структура которых заранее не определена. Кроме этого можно обходить сложные структуры и делать в них довольно сложные изменения и иметь при этом простой и лаконичный код. Ну и банальное обращение через призмы проще, чем исользовать огромный паттерн-матчинг.


Линзы и монады есть и в F#. В виду отсутствия HKT это просто чуть менее удобно, но это с лихвой окупается экосистемой.

Насколько я знаю в шарпе нет трансформеров монад и уж тем более нельзя писать штуки вроде таких:


foo :: (MonadWriter String m, MonadBar m) => Int -> m String

А это один из мощнейших инструментов для:
а) инверсии контроля, а соответственно тестирования и переиспользования кода
б) композиции разных алгебр в tagless final
в) контроля за эффектами по типу (поход в базу, запись в лог, генерация рандомного числа, етк)
Я бы не сказал, что это "просто чуть менее удобно".


Работать на нём — нет спасибо, у меня семья)

Так не кто не говорит вам, что вы должны сейчас же бросить свою работу и идти искать работу на хаскеле. Более того, никто не говорит, что вы вообще хоть что-то должны. Я даже не говорю что хаскель в целом "практичен". Я говорю, что чистота, если абстрагироваться от конкретного состояния IT индустрии — штука вполне себе практичная, а стремление к чистоте не делает что-то непрактичным. Хаскель, например, непрактичным делает малое сообщество, недостаток качественных библиотек и тулинга.

Например линзами можно удобно разбирать сложные JSON и XML, структура которых заранее не определена.

Это всё от лукавого, гораздо проще разбирать неизвестные JSON и XML обычной динамикой, а не линзами. Вы не замечаете как Хаскель подсовывает вам заведомо более сложный и неудобный инструмент для простейшей задачи?


Насколько я знаю в шарпе нет трансформеров монад и уж тем более нельзя писать штуки вроде таких:

Я ж написал — HKT нет. И не уверен что будет.
Ещё в F# нет зав и лин типов. Хочется, конечно, но довольно редко.


Я бы не сказал, что это "просто чуть менее удобно".

А я бы именно так и сказал! Это действительно просто чуть менее удобно.


Например, Idris 2 Хаскелю насуёт по всем статьям, но что-то я не заметил чтобы хаскелисты бросили всё и на Идрис перешли массово) Хотя те же аргументы можно было применить и в обсуждении Haskell vs Idris.
Может кроме офигенных типов надо что-то ещё языку чтобы быть удобным?


Я говорю, что чистота, если абстрагироваться от конкретного состояния IT индустрии — штука вполне себе практичная, а стремление к чистоте не делает что-то непрактичным. Хаскель, например, непрактичным делает малое сообщество, недостаток качественных библиотек и тулинга.

Именно в этом мой поинт про семью и был. Вместо производства продукта, на Хаскеле я буду вынужден за 1 минуту нарисовать красивый хрустальный замок со всей мощью терката и оставшиеся 7ч59мин рабочего времени бороться с экосистемой. Я не люблю велосипеды, я не люблю кодить. Для меня это средство зарабатывания денег, поэтому чем меньше времени я трачу на решение задачи и доведения её до продакшна, тем больше времени у меня остаётся на личные дела.

НЛО прилетело и опубликовало эту надпись здесь
Ну так насуёт. Библиотек действительно мало, пакетного менеджера нет (ipkg несерьёзно), баги в тайпчекере есть и немало.

Я слишком общо сказал про "по всем статьям". Я имел в виду только систему типов и всякие мозговзрывные вещи. Как хасель умеет в монад трансформер по сравнению с F#, так и Идрис умеет много чего по сравнению с Хаскелем.


Интереса ради, а в какой области вы занимаетесь? А то я бы не сказал, что я испытываю какой-то недостаток библиотек в хаскеле. Даже наоборот, хочешь что-то этакое запилить — а оно уже, блин, сделано :(

облачные микросервисы, ETL.
На прошлой работе Azure, на новой тоже Azure.


У F# фора — все SDK для Azure уже написаны)

внезапно, hackage.haskell.org/packages/search?terms=azure (8 items). Большинство, правда, давно не обновлялось, но по-моему тут уже эффект положительной обратной связи: если бы на хаскеле писало больше народу, то библиотеки к ажуре обновлялись бы почаще.
ЗЫ: про amazon вон 180 items, включая обновлявшиеся совсем недавно.
внезапно, hackage.haskell.org/packages/search?terms=azure (8 items). Большинство, правда, давно не обновлялось, но по-моему тут уже эффект положительной обратной связи: если бы на хаскеле писало больше народу, то библиотеки к ажуре обновлялись бы почаще.

Ясно же что этого недостаточно. там только способов аутентификации в облаке с десяток. Managed ID, AD, Azure AD, OAuth, ApiKey и пр… Видов сервисов несколько сотен, а тут всего 8 либ.


Очевидно что для работы с Ажуром на Хаскеле мне придётся велосипедить не один месяц.

НЛО прилетело и опубликовало эту надпись здесь
НЛО прилетело и опубликовало эту надпись здесь
НЛО прилетело и опубликовало эту надпись здесь
мне C# просто лёг на душу, красивый, интуитивно понятный и куда приятнее после дельфи.
По-моему, он даже после Джавы приятнее
плюсую
Ой, а для тех, кто в танке — «точечка нет» за пределы винды вышла в промышленных масштабах?
Ой, а для тех, кто в танке — «точечка нет» за пределы винды вышла в промышленных масштабах?

Я для винды уже пару лет ничего не писал, всё кросс платформенное.
Даже не задумывался о "пределах винды", оно просто уже давно по умолчанию такое, вне виндовое.

Asp.net core Xamarin и Unity давно запределами винды работают.

Переписали проект с .NET на .NET Core. Уже год в проде на линуксе в амазоне.
Полет нормальный.

Рад за вас. Функции хорошо выпрямляют мозги. Когда пообкатаете их, ваш ООП тоже станет лучше. Многие ОО разработчики за деревьями не видят леса. Вместо решения бизнес задачи, они решают проблемы объектов. Я тоже таким был, и тоже наткулся на F#. Сначала возненавидел ОО, но потом, когда пыль осела, внезапно стал намного лучше писать на объектах. Теперь люблю обе парадигмы, в обеих есть своя прелесть. Однако не идиоматичный ОО код теперь бесит чаще и сильнее.

>весь GoF из коробки
И все это на f#? Похоже, вы что-то не договариваете…
НЛО прилетело и опубликовало эту надпись здесь
А вы думаете, я в исходном комментарии на что намекал? Ровно на тоже самое. Это сложно назвать GoF из коробки, потому что это уже другое.
НЛО прилетело и опубликовало эту надпись здесь
Я это понимаю. Поясню еще раз, потому что это очевидно осталось непонятым: когда вы пишете «GoF из коробки», это обычно означает, что реализация паттернов у вас есть готовая. А то, о чем вы рассказываете, это чуть иное — когда большая часть паттернов вам просто становятся не нужны.

Вы тут некую тонкую грань не ощущаете? Нет? Ну и не надо, забудьте.

Они не нужны, потому что де-факто содержатся прямо в языке, или я не так понял суть обсуждения?

НЛО прилетело и опубликовало эту надпись здесь

Некоторые люди говорят, что химия, физика и математика — не творчество. Зачем слушать необразованных людей? ;)

У меня почему то после прочтения этой статьи тепло и хорошо на душе. Спасибо. Душевно так.
А где результат той самой недели?
:) теперь нужно попробовать хаскель
и понять — что все это у людей в головах, а не в языке. Что на любом языке можно так же написать, если только правильно сформулировать для себя.
А пробовал ли автор Kotlin?

Я спрашиваю потому что рассказ похож на мои ощущения при переходе с Java на Kotlin.
При этом я практически не потерял в качестве инструментария, в Intellij IDEA Kotlin поддерживается не хуже Java (только что IDE помедленнее ворочается).

Вот тут есть пример как аналогичный код для F# выглядит на Kotlin
discuss.kotlinlang.org/t/equivalent-kotlin-code-to-my-f-functional-code/6578

Было бы странно если бы Котлин в idea поддерживался хуже, чем java. Все таки они его сами разрабатывают

Имхо таки Kotlin поддерживается похуже, чем Java, по крайней мере полгода назад. Натыкался на менее умную работу статического анализа вроде определения всегда ложных/истинных условий с арифметикой. Код на Java подсвечивается предупреждением, а после встроенной фичи конвертации кода в Kotlin сообщений не видно. Конкретных кейсов не сохранилось, поэтому и сейчас проверить не могу...


И это не странно: Java поддерживают в несколько раз дольше, поэтому и поддержать успели больше...

И это не странно: Java поддерживают в несколько раз дольше, поэтому и поддержать успели больше...

Просто дополнение:
Как по-мне, идея в принципе должна лучше поддерживать джаву и дело не столько в времени, а просто потому, что она изначально писалась именно под джаву. Основной упор был именно на джаву и она прожила с ней огромное количество времени. Какое количество инспекций и рефакторингов было написано под всевозможные версии, библиотеки, фреймворки, JEE и прочие радости жизни? Какое количество разработчиков пользуется котлином и какое джавой? Вопросы риторические.

И, если сейчас поддержка нового языка будет не хуже, то это будет как минимум странно. Команды разработки плагина для нового языка и команда разработки всевозможных инспекций и обработок для джавы, пусть и пересекаются, но у последней, скорее всего, просто больше людей, больше опыта с этим конкретным языком. И поэтому поддержка лучше.
У котлина она хорошая, спору нет, но ожидать такого же уровня поддержку, как в джаве — эээ.

Я думаю похожие эмоции были бы при переходе с Java на C#. Kotlin, пока что, немного приятнее, но имхо совсем немного. Но зато у C# нет проблем, которые идут только из-за jvm и не могут быть нормально решены без изменений именно там. Так что проба F# кажется более внушительным шагом. В jvm стеке, полагаю, стоит называть Scala, а не Kotlin.

Имхо, Kotlin намного свежее выглядит и пишется, чем C#. А про какие проблемы JVM (кроме проблемы с дженериками, которые частично решаются модификатором reified в Kotlin) идет речь?

Да, я про дженерики и вспомнил, reified к сожалению применим только к инлайн ф-циям, ну оно и понятно почему. Ну а насколько Kotlin временно обошел C# не буду спорить. Если бы не грядущий c# 8 с nullability, то сказал бы намного. Классная фича, которая должна была быть с рождения, как в Kotlin.

Генерики все же более общая проблема, например попробуйте на JVM реализовать class Foo : IFoo<Bar>, IFoo<Baz>. Пример немного искусственный, и в некоторых случаях может решаться введением промежуточных iFooBar : IFoo<Bar>, но не всегда.


Второе — в C# экосистеме очень много используется всевозможных анализаторов кода в рантайме. Самый типовой пример: генерация SQL-запроса из foos.Where().Select().ToList(). Это наверно можно сделать на хитрых стримах, но возможности экспрешнов намного шире. Например, я мигрировал на MongoDriver 2.0 и там отсутствовала функция Save (upsert по сути), ну я взял, расчехлил экспрешны, и сделал обобщённый код, работающий со всеми типами. Тут есть вся вкуснятина, включая формирование функции-темплейта, в теле которой заглушка заменяется реальным значением, переданным пользователем (IdConstantVisitor).


Третье — с появлением Roslyn очень распространены стали анализаторы кода на C#. Я не про анализ Java-кода всякими анализаторами, а про бытовые вещи. Например, тут человек просил в язык добавить модификатор видимости, чтобы делать белые/черные списки типов, которые могут вызывать некий код. Берем, тратим 20 минут, и анализатор реализующий функционал готов.


image


Ну и небольшой минусик лично от меня: аннотации. В C# почти всегда можно просто сделать goto атрибута и посмотреть, что именно он делает. А у меня коллеги-котлинисты постоянно жалуются, что висит десяток собак на классе или функции, и не понятно, что они вообще делают, и где правды искать.

НЛО прилетело и опубликовало эту надпись здесь
Аннотации не идиоматичны для котлина, если ваши друзья пишут на котлине и у них на классе висит десяток собак, то они на самом деле скрытные джависты.
Roslyn скорее фича C#, чем минус Котлина :) Я точно так же могу сказать что дескать в C# нет property delegate или инфиксных функций.
Про генерацию я не очень понял пример, можно поподробнее?
Аннотации не идиоматичны для котлина, если ваши друзья пишут на котлине и у них на классе висит десяток собак, то они на самом деле скрытные джависты.

У них котлин со спрингом, и там этих собак тонны


Про генерацию я не очень понял пример, можно поподробнее?

Ну например вы пишете запрос
var foo = MyDb.Employee.Where(x=>x.Sex == Sex.Male).Select(x=>x.Salary).ToArray();


И он транслирует его в какой-нибудь SQL или в mongo-запрос, в зависимости от того, какое хранилище подключили.


Еще удобнее, когда где-то есть визиторы, которые этот экспрешн модифицируют, например, добавляют дополнительно Where(x=>x.AccessRights == GetAccessRightFromCookies()). То есть вы пишете обычные запросы, а где-то дополнительно навешиваются еще условия, что юзер получает только те данные, к которым имеет доступ. Или подменяется часть запроса, чтобы обработать некоторые случаи.

Задело за живое. К сожалению с F# есть одна проблема. Если повезет то ты просто не поймешь что за язык, или будешь пытаться писать на нем ровно так же как пишешь на С# (ставя везде mutable). А вот если не повезет то ты поймешь насколько это крутой и насколько недооцененный язык. Ты уже заразился, для каждой задачи ты уже видишь два решения: C# стиль (с кучой мусора на интерфейсах и DI) или F# стиль. Давным давно я когда то влюбился в C# после нескольких язков и я был счастлив. А сейчас: хорошая зарплата, начальство, риск менеджмент, кадровая политика и т.д. и т.п. прибивают разработку гвоздями к C# но я уже несчастлив. Эта бесконечная вереница интерфейсов, скобочек и безумного количества мусорного кода с пробрасыванием интерфейсов, наследования от интерфесов, где у 99,99% интерфейсов всего одна единственная реализаця. Слава богу есть Resharper, который хотя бы хорошо автоматизирует генерацию этого адского, бесползеного, не приносящего никакой прямой пользы мусора. Но ты понимаешь что можно было бы идти по другому пути — пути где не надо было генерировать и поддерживать этот мусор и ты несчастлив что смалодушничал и выбрал более теплый, мягкий, безопасный путь бесконечного мусорного кода типичной Enterprise разработки.

Попробуйте писать на C# без этого мусора. Я, например, пишу на C# в крупный проект в крупной команде, где не пишут интерфейс, когда есть только одна реализация, где в DI ничего нигде не регистрируется в коде (все автоматически), и все, что DI пробрасывает по умолчанию — Singleton. Я был счастлив найти команду, которая не пишет интерфейс под каждый чих, которая не считает SOLID манной небесной и единственно верным путем.
А юнит тесты как пишете?
На моём текущем проекте именно так ребята и писали несколько лет. В итоге у них у класса, который используется везде, для тестов есть метод GetDebugInstance, я не шучу. И чтобы протестировать одну строку приходится писать под 50-100 строк кода инициализации всего, что завязано друг на друга.

Я заменил ровно одно свойство на возвращение интерфейса вместо конкретного класса и юнит тест снова стал юнит. А вы как делаете?
Пишем только интеграционные тесты

Я работал во многих командах где на C# так и пишут. Но опять таки, как было замечено выше, на C# писать в таком стиле это боль. Когда тебе сдают проект с 1,3 млн. строк кода, без тестов, без организации без структуры (ну и естественно со всеми нарушениями принципа SOLID и DDD). Это боль. Очень большая боль.


Все эти SOLID, DDD, DI, интерфейс на каждый чих и т.п. получили популярность в Enterpise секторе не из за того что разработчики страдают мазохизмом а из за того что они решают конкретную проблему больших проектов.


Просто когда видишь что можно поменять мышление, можно по другому взглянуть на проблему и это позволит убрать этот мусор то уже трудно заставить писать все это.


И почему думаете что SOLID и ФП несовместимы? Если довести SOLID принципы до абсурда то у тебя практически получится функциональный подход. (на самом деле не совсем так но это тема отдельной статьи).


Возьмем например букву S. (Принцип единственной ответственности). Одна функция одна ответственность. Схожий принцип I (принцип разделения интерфейсов) — один интерфейс — один метод — одна функция и т.д. по всем остальным принципам.


Посмотрите еще насколько проще воплощается DDD на F# по сравнению с реализацией DDD на C#.
https://fsharpforfunandprofit.com/ddd/
В больших проектах SOLID и DDD это манна небесная которая реально спасает разработку. Но на F# эти принципы соблюдать еще проще чем на C#

Да, автоматический DI + singleton его же средствами и концептуально получаются некие микромодули которые содержат связанную функциональность и могут декларировать через иньекцию в конструктор свои зависимости от других "модулей".
И я рад бы писать это на функциональщине, но ведь там придётся каррировать руками каждую функцию и пихать необходимые аргументы, вместо "модулей"-классов.


Например некая хранилка документов с возможностью создать/получить/удалить документ. Всем трём функциям нужен клиент к БД. В ООП+DI я добавляю его в конструкторе и использую в методах. В ФП мне нужно объявить его аргументом у всех трёх функций, потом из каждой функции сделать каррированую версию для использования в других местах (сразу скажу, что я не особо писатель на ФП, больше читатель. И много где пишут, мол, используйте каррирование и всё будет хорошо, но может быть я что-то упускаю?).

Ну для начала вам никто не запрещает делать классы в ФП :)


Но если хочется чистоты и фпшности (в описанном случае смысла вижу мало упарываться), то делаем одну функцию с параметром dbClient, которая возвращает рекорд (тупль) из 3х функций (create/read/delete), которые работают с этой db. Во все три уже будет вшит dbClient.


Я бы так не делал.

классы в ФП

Да в F# думаю оптимальным будет структуру приложения делать на классах/интерфейсах, а мощь ФП использовать локально внутри.
Но вот в хаскеле классов нет :(


которая возвращает рекорд (тупль) из 3х функций

не, это упячка :)

не, ну зачем сразу тупль. Надо либо record, либо экземпляр какого-то типа, который является инстанцией подходящего type class (это два подхода к реализации подобных вещей, у каждого есть плюсы и минусы, противники и сторонники, а по сути — баш на баш). Технически ничем не отличается от сишечных структур, содержащих функции.

data DbClient = DbClient {
    create :: Entity -> IO (),
    read :: PrimaryKey -> IO Entity,
    delete :: PrimaryKey -> IO ()
  }

realDb :: DbClient
realDb = DbClient {
   create entity = ...
}

fakeDb :: DbClient
fakeDb = DbClient {...}


Технически, дальше вам никто не запретит написать
-- объявляем класс (ну ладно, не класс, а структуру с методами)
data SomethingInterestingDoer = SomethingInterestingDoer {
  dbClient :: DbClient,
  -- другие поля
  doSomethingInteresting :: IO ()
}

makeDbClient :: ConnectionString -> DbClient
makeDbClient = ...

-- экземпляр класса с реализацией методов
something :: ConnectionString -> SomethingIntestingDoer
somehting connStr = doer
  where doer = SomethingInterestingDoer {
    dbClient = makeDbClient connStr, -- это мы "добавили в конструкторе"
     doSomethingInteresting = do
        create (dbClient doer) newEntity -- а это мы используем dbClient
     }

это 1-в-1 «оопэшное» решение. Только обычно так не пишут, если нет большой нужды. Обычно пишут проще:
doSomething :: ConnectionString -> IO ()
doSomething connStr = do
   let dbClient = makeDbClient connStr
   create dbClient myEntity


(я тут игнорирую кучу деталей, на данном уровне абстракции непонятно кто такой ConnectionString, makeDbClient должен зависеть от реализации самого клиента, итд)

Только в таком решении всё равно нет автоматического резолвинга зависимостей, "добавленных в конструкторе" :)
Я видел какую-то реализацию автоматики на классах типов в хаскеле, но она работала за счёт того, что инстанс для каждого класса был один, но в такой реализации это в тестах довольно бесполезно.

так а какая замена скажем интерфейсам и DI в F# есть?
так а какая замена скажем интерфейсам и DI в F# есть?

Ну для начала, в F# есть интерфейсы и DI :)
Но чаще всего можно обойтись partial apply.


Марк Симан (автор Dependency Injection in .NET) рассказал об этом на прошлом DotNext:
https://www.youtube.com/watch?v=xG5qP5AWQws

Во-первых, можно использовать все то же самое (но лучше этого не делать)
Во-вторых, функции, особенно в F#, очень легко композируются.
Если делать именно dependency injection, то для этого помогает partial application, т.е вы просто указываете в вашей функции аргументами все необходимые зависимости, а реальный инпут указываете в самом конце:


let getUser getUserDtoFromDb mapUserDto userId =
    userId |> (getUserDtoFromDb >> mapUserDto) // пихаем айдишник в функцию
//созданную на лету из наших двух с помощью оператора ">>"

let getUserImpl = getUser MyRepo.getUser MyMapper.mapUser // передаем зависимости (2 параметра из 3 необходимых, и получаем функцию, которая принимает айдишник и возвращает юзера из базы

Но гораздо лучше делать dependency rejection и луковую архитектуру. Функции все так же будут легко композироваться, но будут более гранулярными и легче тестироваться.

НЛО прилетело и опубликовало эту надпись здесь
НЛО прилетело и опубликовало эту надпись здесь
Вот состояние прям как у меня сейчас :(
Тебе за 30, семья, дети, ипотека, ЗП не хватает(и к сожалению повышать не собираются), ты являешься не официальным разрабом при отделе(хоть и очень крупной компании РФ), твой культ Delphi/Pascal, но сейчас пишешь(уже только иногда) для офисного планктона макросики, да инструменты на VBA(Excel), поддерживаешь те оставшиеся инструменты, которые остались после оптимизации отдела, при этом ты владеешь PHP(но не имеешь опыта, кроме домашних поделок), базовое понимание SQL и умение проектирования БД(с нуля) в My/MS SQL, способность с нуля создать/сопровождать многопользовательскую систему, как говорится «из подручных» и доступных, в наших бюрократических условиях, средств. Но все попытки перевода в специализированные отделы разрабов сводятся к отсутствию опыта именно вот по тем новомодным технологиям которые нужны именно сейчас, хотя время на освоение не более месяца хватит для адаптации к этим «яйцам», ну а тонкости с опытом.
И вот сидишь и руки опускаются. У себя в отделе тебя ценят уважают, знают на что способен и как это оптимизировало процессы, но ЗП не могут поднять т.к. не от них зависит, а от долбанных стандартов и новой политики, нового руководства, а соседние отделы еще на этапе собеседования, смотрят на тебя как на студента-самоучку(выскачку) и впринципе опыт/умения не интересует т.к. это же Васик, не топовый язык. Вот тут руки и опускаются.
Спасибо. Очень воодушевила Ваша история. )))

П.С.: Сорри. Крик души…
> базовое понимание SQL и умение проектирования БД(с нуля) в My/MS SQL
впервые вижу такое в одном предложении))) умение создавать таблички и накидывать в них новые поля — это еще не умение проектировать БД)

Попробуйте освоить какой нить новомодный язык программирования (типа Go или NodeJS), попрактикуйтесь в решении сколько нибудь серьезных задач, посмотрите как люди пишут производственные приложения или полистайте код на github. Сменить профиль IT не так сложно как кажется, поверьте.
NodeJs это не язык программирования, это платформа…
попрактикуйтесь в решении сколько нибудь серьезных задач,


Серьезная задача — та, которая исходит от бизнеса, а не от графомании. Поэтому непонятно откуда брать эту самую задачу, если бизнесу все эти лампочки, процессоры, синлтоны с роутерами и пр. до фонаря, в отличие от проблем с клиентами и деньгами на счетах.
Может стоит уйти джуном в нормальную контору, где дадут возможность прокачаться разрабом? Если такое рассматривать, то лучше сейчас — к 40 будет куда сложнее. Брать проекты на стороне, не бояться отсутствия опыта и просто долбить в одно место, пока не заработает. Да, много времени уйдет, но результат будет. Все это говорю по личному опыту переквалификации из экономиста в web dev, потом в embedded electronics, потом обратно в web dev (не считая забегов в desktop, когда клиенты сильно просили).
Опишу свою историю, может вас к чему-то подтолкнет.
Я в 24 года, после работы экономистом-бухгалтером, пришел в крупный банк на непонятную позицию (в новом подразделении, то ли аналитик, то ли недоразработчик-писатель макросов на VBA). И так сошлись звезды, что после принятия меня на эту должность, одновременно с начальником (отдел-то новый), он оценил, что я не подхожу под эту должность (не знал SQL) и направил меня на 4 платных майкрософтовских курса по MS SQL и разработке DWH на нем. Через несколько месяцев, сразу после последнего моего курса начальника уволили, взяли другого, но и тот убежал через 3 недели. Я уже тоже готовился писать заявление (было абсолютно не понятно что от нас хотят, но чего-то требовали), но решил остаться и посмотреть что будет дальше.

1. Следующие 7-8 месяцев я на практике изучал и игрался с MS SQL с правами админа. Параллельно работодатель оплачивал мне изучение языка C# на рабочем месте (как и у автора поста, работодатель про это не знал). Сначала писал легкие маленькие скриптики в MS SSIS, затем расширения для MS Excel. Ну и какую-то работу тоже работал.
2. Перешел в не ИТ-компанию даже с небольшим повышением в зп (искал специально, нашел совсем не сразу, отшивали из-за высоких запросов по зп) на стажера-джуна на C#.
3. Отработал там ровно 1 год и ушел в одну из крупнейших ИТ-контор в РФ на позицию middle+

Итого, на то, чтобы мутировать из экономиста, умеющего немного говнокодить на VBA, в middle+ C# разраба, у меня ушло чуть больше полутора лет. Вам, полагаю, стоит приступать сразу к пункту 2.

/offtop:


Что за инвайт-рекурсия??

image

Это приглашение, полученное в честь запуска английской версии Хабра:
каждому пользователю с положительной кармой мы начислим сегодня по одному приглашению.

У меня, собственно, у самого такое же.

А зачем его на самого себя тратить то?

Оно у всех ещё не приглашенных пользователей (т.е. Read & Comment) потратилось «на себя» автоматически.
Фатальная комбинация технологии и предметной области. Убирай вообще опыт из резюме, гооври что переучился из аналитика (всё-равно никто не знает кто это и что должны уметь).
Так уж получилось, что «с детства» недолюбливаю .NET и все что с ним связано, особенно нелепо для меня выглядят решения реализованные с использованием .NET без контекста использования в среде Windows. Из текста статьи осмелюсь предположить, что автор до использования F# писал только C#, что в общем прискорбно.
Зачем устраивать холивар, если ты зашел под пост о технологии с которой ты плохо знаком, веди себя как гость
— rwx rwx r — -
Более того, это первый комментарий у этого пользователя на хабре.
Хотя зарегистрирован он в 2014 году.
Т.е. человек насктолько не любит дотнет, что не удержался и прервал пятилетнее молчание только для того, чтобы об этом написать)
Причём без каких-либо аргументов. Просто не люблю и всё тут)
Я считаю, что такие инструменты как .NET равно как и Java с ее JVM уводят этот мир в бездну не оптимальности плодя монструозные приложения с детским кодом, но большим аппетитом к памяти и процессорному времени, которые потом считаются нормой. А потом мы видим статьи типа этой "Моё разочарование в софте". Да, не всем нравится писать приложения на не слишком дружелюбных языках типа C++, да и времени нет, все понятно. Но есть же такие творения как Go, которые еще вселяют надежду, что не все потеряно…
Так и знал, что вы не удержитесь и всё-таки поведаете почему же вы так не любите дотнет)
Вы даже не замечаете насколько ваш комментарий нерелевантен по отношению к данной статье. Она ведь не про дотнет и даже не про F#. Она про то, как изучение нового языка/технологии/чего-то ещё может открыть второе дыхание у перегоревшего специалиста.

P. S.: Люблю Го, но вот за таких вот представителей его сообщества иногда стыдно.
Как это все знакомо, годы спустя тоже к этому пришел: «Но настает ночь, отвлекающие дела заканчиваются, отмазки тоже, и я остаюсь один на один с разочарованиями и бессонницей — я ни на что не годен, ничего ни с чем никогда не получится.»

Да хватит уже выгорать. Смотришь твиттер — этот выгорел, тот выгорел. Посты на три экрана. Проблема преувеличена.


я пошел к начальству и попросил меня уволить

А что еще делать начальнику? Надо не просить уволить, а увольняться. Иначе в его глазах вы выглядите как капризная телочка, которая не знает, что ей нужно. Насколько я понял, после этого вы не уволились, то есть подтвердили мнение начальника.


Кодить по ночам — отстой. Это нехватка сна, нерподуктивный день и возбуждение перед сном. Снова кодинг ночью, и так по кругу.

НЛО прилетело и опубликовало эту надпись здесь

Я не писал, что отрицаю депрессию. Депрессию нужно лечить, бороться с ней. А ночной кодинг и примерзжая к губам сигарета этому не способствуют. Это инфантильный романтизм, упивание собственным страданием. Жаль, что на такое ведутся толпы людей. Срабатывает принцип "это обо мне", все считают себя тоже выгоревшими и пишут посты.

НЛО прилетело и опубликовало эту надпись здесь

Стоит заметить, что это не диагноз.


Кстати, ряд специалистов считают, что и выгорание — это не отдельная медицинская категория, а одна из форм невротической депрессии.

Экстраполяция себя любимого на весь мир — это наше все. Если я не испытываю от работы никаких эмоций — то это правильно и у всех должно быть так-же, да? Программирование, как вид деятельности, вполне располагает к "мукам творчества", если вы не человек-функция, клепающая одинаковые формочки. А для многих кодинг еще и базовое средство самовыражения, центр притяжения для всей жизненной философии. И не говорите, что это плохо.

«Проблема преувеличена» — это газлайтинг с вашей стороны.

Это не газлайтинг, а попытка нормировать, чтобы не лезло через край. Подробней написал у себя.

Отрицание значимости чего-либо для другого человека — это автоматически газлайтинг.
Блин, «газлайтинг» сейчас растянули из очень редкого вида психологического насилидя до любого «ты не прав»

Я на 98% уверен что igrishaev абсолютно искренне не верит в выгорание. Что сказать, возможно он и правда не сталкивался с ним ни разу до того как первый раз прочитал, бывает.

Пост его, офк, чистое жлобство, издеваться над людьми страдающими психической болезнью за то что им хочется внимания и поддержки это какой-то стук со дна. И сразу похвастаться что он-то не выгорает.(а следовательно понятия не имеет каково это болеть выгоранием, ага)

Ну и в конце доля душевного стриптиза о том как у него мгновенно меняется настроение и мировоззрение от впечатлений за день(поданное под соусом будто это естественно и у всех так)

Меня от таких постов просто детонирует, нет ничего отвратительнее морализаторских постов от «богатых и здоровых» о том как «бедные и больные» всё придумывают, их проблемы не настоящие, а вот он-то герой все проблемы(которых у него не было) одной силой воли преодолел.

И еще позвольте спросить — так вы пишете на F# в прод за деньги, или это хобби? Из поста это не понятно.


Пока это хобби, вы в пузыре и сами себе хозяин. Вас радует не язык, а свобода от надоевших правил. Начнете писать в прод — бОльшая часть проблем вернется на круги своя.


Спрашиваю, потому что знаю по опыту — даже самый экзотичный язык меркнет в повседневной работе. В моем случае это Clojure. Переключение на функциональный язык сперва окрыляет, но в итоге ты выигрываешь не так много, как думал сначале.

Спрашиваю, потому что знаю по опыту — даже самый экзотичный язык меркнет в повседневной работе. В моем случае это Clojure. Переключение на функциональный язык сперва окрыляет, но в итоге ты выигрываешь не так много, как думал сначале.

Не думали написать статью об этом в разрезе Clojure? Статей про этот язык маловато, а статей о промышленном использовании, с примерами и проблемами и вовсе не припоминаю.
НЛО прилетело и опубликовало эту надпись здесь
Это так на вскидку: www.youtube.com/watch?v=iUC7noGU1mQ
Там ютутб еще пяток нормльных отчётов в рекомендациях выкатит точно.
Пишу в прод. Полет отличный, минусов самой работы конечно не компенсирует, но минусов от ненавистного языка стало меньше.

Я, конечно, понимаю, что тут поётся ода F#, но


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

Для черни?

Конечно же. Голубая кровь даже за два часа (10 км пешком) при температуре минус 30 не замерзает.
)))
НЛО прилетело и опубликовало эту надпись здесь

Неочевидная. 10 км пешком или 30 минут на общественном транспорте — лично для меня выбор очевиден.

Очевидно, что автор описывает свои ощущение в момент ненависти к этому миру.
Предлагаю в ответ говорить F# для черни.
Я растерял веру в разработку, выгорел, но меня спас проект, который я начал делать в качестве хобби

Если абстрагироваться от деталей, то напоминает рассказы тех, кто ударились в религию после тяжелых событий.

Психотип автора не подходит для разработчика, скорее для автора стартапа, т.е. он занялся не своим делом, потому все ему выглядит тупо и уныло.
Да черт возьми, как же Вы круто пишете!!! А данная статья вызвала у меня такие эмоции, как будто я читал ее не на рабочем месте в попыхах, пока прогружается среда, а дома с горячим чаем, удобно устроившись на диване)))
Но ведь никто не заставляет вас слепо следовать книгам, C# поддерживает все парадигмы программирования и не он заставляет делать инструменты ради инструментов.
Я пишу на C# уже 10 лет, но не столкнулся с тем что говорит автор и вы. Возможно потому что начал читать книги по нему, паттернам и подходам уже после того как дошел до middle уровня. В результате у меня есть набор библиотек применяя которые остается писать только чистую бизнес логику.
Даже приведу пример из тестового проекта, ниже весь код микросервиса. Для понимания, это второй сервис в цепочке, отвечает за преобразование сырых данных во внутренний формат, принимает сырые данные по транспортному соединению от сервиса читающего данные с сайта, после преобразования передает следующему сервису который отвечает за планирование доставки готового документа.

Program.cs
namespace Adapter
{
    class Program
    {
        static void Main(string[] args)
        {
            BusinessApplication.Startup<AdapterService>(args);
        }
    }
}


AdapterService.cs
namespace Adapter
{
    public sealed class AdapterService
         : AdapterExchangeService<OriginalEntry, Document>
    {
        protected override Document Convert(OriginalEntry incoming, Guid frameId)
        {
            Log.Debug($"New quote: {incoming.Title}");
            var doc = new Document(frameId);
            doc.Header = incoming.Title;
            doc.Identifier.DateLabel = incoming.PublishTime.ToString("yyyyMMdd");
            doc.Identifier.Timestamp = incoming.PublishTime.Ticks.ToString();
            var paragraph = new Paragraph();
            paragraph.Append(new Text(incoming.Content));
            doc.Content.Sections.Add(new Section { Parts = new System.Collections.Generic.List<IContentElement> { paragraph } });
            doc.DescriptiveMetadata.CopyrightNotice = "Bash.Im";
            doc.DescriptiveMetadata.Created = incoming.PublishTime;
            doc.DescriptiveMetadata.Language = "RUS";
            doc.DescriptiveMetadata.Source = new Agency { Title = "bash.im", Url = "https://bash.im" };
            doc.DescriptiveMetadata.Original = new Tag { Name = "href", Value = incoming.Link };
            return doc;
        }
    }
}


Это весь код сервиса, при этом, скомпиленное приложение умеет запускаться интерактивно и как служба, умеет устанавливать и удалять себя в системе. Регистрируется в service discovery и принимает данные от других сервисов, и передает данные после обработки дальше. Логируются все сбои и процесс работы. И т.д. Даже умеет горизонтально масштабироваться. И я не вижу аргументов по которым стоит менять язык. Но буду рад услышать ваши, чем плох такой подход, и чем спасет F#.
Не совсем понятно, в истории, где вы выгорели и попросили себя уволить, вы писали, что вы честно исследовали сложный баг, и просто длительное время никуда не продвигались. И это вызывало у меня сочувствие.

Здесь же вы пишите «На ломанном английском я откровенно врал: «ол паст вик ай серч фор баг. Стил ноу саксес. Вил континью»»
То есть, раз врали, значит вы ничего и не делали по задаче? Честно говоря, под таким углом это выглядит совсем по-другому.

А если нет, то в чем ложь?
Это выглядит странно со стороны, но если бы вы прожили тот день вместо меня, вы бы реагировали также. Думаю, что так у всех культистов технологий. Они влюбились в свои япы, потому что обстоятельства, при которых они с ними познакомились, очень остры лично для них.

Как же я понимаю автора. В дни тяжёлой депрессии я просто беру свой старый проект на своём любимом языке программирования и просто пишу — один кусок, другой, придерживаюсь стандарта который беру за основу. Это ненадолго отвлекает и если заглушить в себе мысль "это никому не нужно", то можно просто помедитировать за написанием кода. Расслабляет лучше, чем алкоголь и всякие антидепрессанты

И вам я тоже хочу адресовать вопрос, что задал автору: «как должно быть, чтобы вы ощущали душевный подъем?»

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


Как должно быть

Сложно на самом деле сказать. Это не какая-то определённая атмосфера или ритуалы. Просто я люблю программировать — мне нравится мой язык программирования, выбранный framework, нравится доходить до состояния осознания программы не как набора методов, классов, циклов и алгоритмов, а как непрерывного потока информации и данных, который я направляю в нужное мне русло. Из-за этого мне очень нравится Git — он напоминает реки кода, которые разливаются и сливаются вновь.


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


Так случилось, что слова автора...


Они влюбились в свои япы, потому что обстоятельства, при которых они с ними познакомились, очень остры лично для них

… глубоко запали мне в душу, потому что программировать я начал в 14, когда у меня действительно была глубокая депрессия и программирование до сих пор позволяет мне абстрагироваться от мира, от суеты и от людей, которые её создают — здесь всё логично, строго и никакого хаоса, кроме того, в котором повинен сам. Меньше говнокода хаоса — больше умиротворения. Так что я полностью согласен с автором — культ инструмента действительно помогает не выгореть, не пропасть в депрессии и не сойти с ума, потому что работа с ним доставляет удовольствие

Наверняка где-то за это благодарны и хорошо платят. Стоит узнать где :)
«здесь всё логично, строго и никакого хаоса» — до меня в текущем проекте работало 3 команды, в общем человек 50, хаос это мягко сказано, чтоб что-то понять надо выйти на 10й уровень.
Может попробовать собрать совместимых разработчиков, придумать интересный проект и на себя поработать. Можно дело в несовместимом коллективе? Может именно в этой не совместимости и есть суть профессионального выгорания? Может хочется над чем-то глобальным, своим работать? Проблема выгорания и человеческой несовместимости самое главная проблема. И вот походу ее решение psycalc.github.io
У вас получилась какая-то ложная дихотомия — либо «C# и уныние», либо «F# и процветание». И выходит как в известной картинке:
Спойлер


А на самом деле корень проблемы был в унылости работы, с ее энтерпрайзными подходами и унылыми задачами, а не в инструменте, которым эти задачи решались.
«Я часто критикую технологии, которые кажутся мне неправильными, и в ответ получаю… в морду»
На кого рассчитан этот текст? За 25 лет в ИТ передо мной сменились десятки технологий и сотни людей, и я ни разу не видел человека способного за критику технологий дать в морду. Автор переигрывает.
НЛО прилетело и опубликовало эту надпись здесь
Возможно, чтобы было интереснее лучше идти в игрострой)
И никто не написал про огнетушитель…
Для меня программирование это неведомый мир где общаются люди в серебристых одеждах на языках не похожих ни на один земной. Но очень интересно было следить за переживаниями автора. Хочется его спросить: автор, а что тебе нравится, что делает тебя счастливым? Какая деятельность?
НЛО прилетело и опубликовало эту надпись здесь
Я не сказать хочу, а узнать.
А не хотите ли попробовать Perl?
он же умер уже лет пять как, нет?
Он как фортран. Думаешь умер, а реально без него полмира сломается.

Именно. Как может умереть топовый язык?


Даже если он и умер, то на мой век хватит. Он мне нравится, я его люблю: он прост и гибок. А всякое говно, которое приводят в примерах по поводу перл, можно писать на любом языке. Просто этих "примеров" на перл больше… =(

НЛО прилетело и опубликовало эту надпись здесь

Почему умер? я успешно на нём программирую уже лет, эдак, 15. По статистики ActiveState в последние годы активность проектов на Perl возросла.


Вот например последние 2 года я переписывал проект построенный модуле Mason, первая версия которого вышла в 1998году!


Очень даже хороший boost для бизнеса, когда всё работало годы и никто ничего не трогал. За это я и люблю Perl. Спасибо разработчикам за совместимость!


Вообще не понимаю как люди верят в этот булшит по поводу "Перл умер", если он является топовым языком все эти годы...

Обратите внимание что автор никому из вас не ответил в комментариях. И судя по содержанию статей которые он уже успел написать, автор профессиональный тролль(ИМХО) =)
Какая-то «нездоровая» ситуация. Мне кажется автор выбрал не ту профессию
Что читать по F#?
Что читать по F#?

Можно начать отсюда:
https://fsharpforfunandprofit.com/why-use-fsharp/


По мнению подавляющего большинства F#истов, лучший сайт для обучения

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Изменить настройки темы

Истории