Очень простой ответ — тулинг, инфраструктура, поддержка крупных/крупнейших компаний.
F# — это экосистема .NET (все нугеты в вашем распоряжении, интеграции со всем на свете).
Нативная поддержка облаков (Azure/AWS). Хаскель туда только через докер пихать или бинарники в виртуалке, а вот F# можно прям в Azure Function или AWS Lambda без прокладок или через WebApp в Azure
Комплиятор и SDK встроены в .NET Core SDK, так что уже даже ничего устнавливать не надо, всё в коробке.
Одна из лучших (на мой взгляд вообще и лучшая) IDE — Visual Studio без вопросов работает с F#, миксовать проекты в одном солюшне и делать референсы между проектами на C#/F# очевидно можно.
F# язык для работы. Haskell для души. Это не значит что на F# нельзя для души, а на Haskell работать, просто разные цели ставят перед собой авторы языков.
Как выше сказано — топ-левел аннотации порядочные люди все равно пишут, а локальный вывод есть уже ну везде, в том числе и в шарпе.
Ну локального вывода маловато, достаточно заглянуть на сорсы LINQ, кошмар же. Бойлерплейт ради бойлерплейта и читабельности не добавляют все эти описания дженериков.
Коллеги недавно ездили в Молдавию получать визу США. На всё ушла неделя, местное консульство скучает, очередей нет, выдают быстро.
У коллег только Российское гражданство, ничего необычного.
За месяц можно успеть сделать, было бы желание сгонять в Молдавию (например).
На Московском консульстве свет клином не сошёлся.
Из него логически следует апи, которое реализует код приведенных листингов. Всё остальное — суть костыли и оверинженеринг, как и почти всё в scala...
Считаю Go слишком переусложнён, память (RAM) есть у всех. Из этого логически следует апи работы с памятью (поинтер, malloc, free). Всё остальное — суть костыли и оверинжениринг, как и почти всё в Go. Апи работы с памятью не содержит требований к работе с ней как с линкед листом, или как с деревом например, т.к. все структуры данных можно реализовать через голые поинтеры.
При прямой работе с памятью программист волен сам выбирать структуру данных для участка памяти, исходя из оптимального сочетания О-сложностей операций работы с этим участком памяти. Как правило это массив или хэш таблица. А не куча, навязываемая маргинальным Go в качестве универсального контейнера для участка памяти.
При такой работе, поинтер на участок памяти может быть чем угодно, лишь бы у вас был этот поинтер — массивом, хэш-таблицей, деревом или ещё чем-то. Это бонус кода при прямой работе с памятью, в более лучшей модульности, а не недостаток как вы тут пытаетесь это представить. Для одних участков памяти объединение c O(1) имеет место быть, для других нет. Соответственно нет нужды добавлять эту функциональность в божественные две функции — free + malloc, создавая бессмысленную мешанину из логических концепций
Возможно, потому что я «забыл» для этого установить какую нибудь vs2018 на 30+ гБ. Увы, внутрь Seq.map я всё ещё попасть не могу чтобы посмотреть значение её второго аргумента.
Это только Ваша проблема. Можно поставить VS Code (40 мегабайт осилите?).
Тот же пример с работающим брекпоинтом в VS Code:
проблемы эффективности функциональных и неизменяемых структур данных
У них есть как плюсы, так и минусы. Когда минусы перевешивают плюсы в F# достаточно объявить идентификатор как "mutable"
неоправданный рост когнитивной нагрузки на чтение и понимание кода.
Сильно Linq увеличивает когнитивную нагрузку на программиста? Вроде наоборот снижает.
функциональный код невозможно нормально отлаживать, дебагер не может перейти внутрь однострочного лямбда выражения, из которых состоит типичный ФП код.
да всё он может, хватит придумывать.
Брекпоинт внутрь однострочной лямбды:
Кажется, когда-то на гитхабе в репозитории Roslyn видел в issues подобный proposal, но с ним что-то было не так. Хотя в C++/CLI такой синтаксис есть и все проблемы решить смогли.
Тем не менее решение некоторых задач, гораздо эффективнее находясь ближе к реальному железу, а не к идеалам. И это факт.
Решение подавляющего большинства задач гораздо эффективнее если находиться как можно дальше от железа. В идеале бы иметь одну кнопку — "сделай хорошо", но пока приходится общаться с машиной на языках программирования и редко-редко опускаться на уровень железа для числодробилок.
А для тех редких случаев когда нужна прям мега оптимизация как на асме — C/C++
Уже думаю, может, лучше вернуться к старому доброму ручному созданию потоков с примитивами синхронизации…
Лучше вряд ли получится, но в .Net есть другие либы для работы с асинхронностью, где всё чуть более детерминированно — F# Async (и к нему в нагрузку AsyncSeq), Hopac (и туда же Hopac.Streams)
Ещё как вариант Rx.Net, для UI норм
И упомяну Akka.Net (и Akka.Streams) — универсальный солдат, работает на тасках, шедулеры там вроде свои написаны, но модель акторов абстрагирует от большей части дичи связанной с TPL
Очень простой ответ — тулинг, инфраструктура, поддержка крупных/крупнейших компаний.
F# — это экосистема .NET (все нугеты в вашем распоряжении, интеграции со всем на свете).
Нативная поддержка облаков (Azure/AWS). Хаскель туда только через докер пихать или бинарники в виртуалке, а вот F# можно прям в Azure Function или AWS Lambda без прокладок или через WebApp в Azure
Комплиятор и SDK встроены в .NET Core SDK, так что уже даже ничего устнавливать не надо, всё в коробке.
Одна из лучших (на мой взгляд вообще и лучшая) IDE — Visual Studio без вопросов работает с F#, миксовать проекты в одном солюшне и делать референсы между проектами на C#/F# очевидно можно.
F# язык для работы. Haskell для души. Это не значит что на F# нельзя для души, а на Haskell работать, просто разные цели ставят перед собой авторы языков.
Ну локального вывода маловато, достаточно заглянуть на сорсы LINQ, кошмар же. Бойлерплейт ради бойлерплейта и читабельности не добавляют все эти описания дженериков.
В .NET такое есть. А в C# — нет.
Code Quotations
Коллеги недавно ездили в Молдавию получать визу США. На всё ушла неделя, местное консульство скучает, очередей нет, выдают быстро.
У коллег только Российское гражданство, ничего необычного.
За месяц можно успеть сделать, было бы желание сгонять в Молдавию (например).
На Московском консульстве свет клином не сошёлся.
И ни слова о Jet.com, который собственно и является тем самым (выкупленным) облачным онлайн-магазином Walmart, догоняющим Amazon.
Считаю Go слишком переусложнён, память (RAM) есть у всех. Из этого логически следует апи работы с памятью (поинтер, malloc, free). Всё остальное — суть костыли и оверинжениринг, как и почти всё в Go. Апи работы с памятью не содержит требований к работе с ней как с линкед листом, или как с деревом например, т.к. все структуры данных можно реализовать через голые поинтеры.
При прямой работе с памятью программист волен сам выбирать структуру данных для участка памяти, исходя из оптимального сочетания О-сложностей операций работы с этим участком памяти. Как правило это массив или хэш таблица. А не куча, навязываемая маргинальным Go в качестве универсального контейнера для участка памяти.
При такой работе, поинтер на участок памяти может быть чем угодно, лишь бы у вас был этот поинтер — массивом, хэш-таблицей, деревом или ещё чем-то. Это бонус кода при прямой работе с памятью, в более лучшей модульности, а не недостаток как вы тут пытаетесь это представить. Для одних участков памяти объединение c O(1) имеет место быть, для других нет. Соответственно нет нужды добавлять эту функциональность в божественные две функции — free + malloc, создавая бессмысленную мешанину из логических концепций
/s
Это только Ваша проблема. Можно поставить VS Code (40 мегабайт осилите?).

Тот же пример с работающим брекпоинтом в VS Code:
Окошко Locals:

У них есть как плюсы, так и минусы. Когда минусы перевешивают плюсы в F# достаточно объявить идентификатор как "mutable"
Сильно Linq увеличивает когнитивную нагрузку на программиста? Вроде наоборот снижает.
да всё он может, хватит придумывать.

Брекпоинт внутрь однострочной лямбды:
Я больше скажу. Закон всемирного тяготения работал и до открытия его Ньютоном!
В F# так и сделано, так что C# просто тормозит.
Можно "как на стеке", можно явно скоупы задавать:
Это прожект манагер же, а не архитектор.
Решение подавляющего большинства задач гораздо эффективнее если находиться как можно дальше от железа. В идеале бы иметь одну кнопку — "сделай хорошо", но пока приходится общаться с машиной на языках программирования и редко-редко опускаться на уровень железа для числодробилок.
А для тех редких случаев когда нужна прям мега оптимизация как на асме — C/C++
Если что, главный по C# вот этот парень
Какую проблему решит Nemerle-2 по сравнению с C#, F# (и чо уж там, Nemerle-1)?
IObservable — push-based stream
async IEnumerable — pull-based stream
Когда-то тоже была такая задача, выбрал Akka.net и её персистентных акторов.
В основном потому что язык создания стейт машин для масс транзита показался уж слишком неудобным
BigInteger в JS нет чтоль?
Added: чтобы не плодить коменты: 1ая задача на F#. фп, чистые функции, вот это вот всё
del
Не, офисный энтерпрайзный планктон плотно сидит на Office365, где ворд и вообще весь офис, тимс, скайп давно в браузере.
Could you also test F# Hopac (which is the same async model as Go)?..
I predict it will be dramatically faster than C# and Go.
Лучше вряд ли получится, но в .Net есть другие либы для работы с асинхронностью, где всё чуть более детерминированно — F# Async (и к нему в нагрузку AsyncSeq), Hopac (и туда же Hopac.Streams)
Ещё как вариант Rx.Net, для UI норм
И упомяну Akka.Net (и Akka.Streams) — универсальный солдат, работает на тасках, шедулеры там вроде свои написаны, но модель акторов абстрагирует от большей части дичи связанной с TPL