Как стать автором
Поиск
Написать публикацию
Обновить
16.12

Функциональное программирование *

От Lisp до Haskell

Сначала показывать
Порог рейтинга
Уровень сложности

POP-lang — воображаемый функциональный язык, основанный на Dependency injection

Время на прочтение7 мин
Количество просмотров1.6K

Вы когда‑нибудь замечали, что pattern matching и Dependency Injection чем‑то похожи? Я — да. Вообще, pattern matching, характерный для функциональных языков, матчит значения только по структуре и содержимому. Вызовы функций не разрешаются. Я подумал — что, если разрешить вызовы функций? В этом случае, мы получим нечто близкое к Dependency Injection.

MiddleAges(status, lifespan) = hipster

Вот так можно попробовать сматчить хипстера, отправив его в средневековье — чтобы узнать социальный статус, который он там займёт, а также его время жизни там. MiddleAges — это некоторая функция. Можно оставить слева только status или только lifespan, хотя, конечно, всем любопытно узнать и то, и другое. Похоже ведь на Dependency Injection?

В этой статье я попытался представить себе, как бы мог выглядеть функциональный язык, основанный на таких конструкциях. Спойлер: в нём есть оператор pop.

Читать

Обработка исключений в Java с использованием сопоставления с образцом (pattern matching)

Уровень сложностиСредний
Время на прочтение7 мин
Количество просмотров7.5K

Обработка исключений в Java с использованием сопоставления с образцом (pattern matching).


Данная статья является логическим продолжением статей



В данной статье рассмотрим способы обработки исключений Java при помощи pattern-matching, как это делается в других FP языках.


Пример на других языках


В функциональных языках программирования существуют удобные средства для работы с исключениями. В Kotlin и Rust это класс Result, в Scala и Haskell — Try. Обработка успешного результата или ошибки может производится при помощи pattern-matching как на примерах ниже.


Scala


val result = divideWithTry(10, 0) match {
  case Success(i) => i
  case Failure(DivideByZero()) => None
}

Rust


    let greeting_file_result = File::open("hello.txt");
    let greeting_file = match greeting_file_result {
        Ok(file) => file,
        Err(error) => panic!("Problem opening the file: {:?}", error),
    };

Использование pattern-matching является естественным (idiomatic) в функциональных языках. А как дело обстоит в Java?

Читать дальше →

Развёртывание программных систем в Kubernetes с помощью Jsonnet

Уровень сложностиСредний
Время на прочтение10 мин
Количество просмотров5.8K

Kubernetes (k8s) является де-факто стандартом для развёртывания приложений. В терминах K8s приложение представляет собой набор сконфигурированных ресурсов нескольких типов — pod, service, deployment, secret, statefulset,… Конфигурация каждого ресурса задаётся унифицированно с помощью YAML (или JSON) манифеста. Kubernetes API и интерфейс командной строки позволяют манипулировать манифестами ресурсов, а сами ресурсы автоматически приводятся в состояние, соответствующее манифестам.


Для формирования согласованных конфигураций ресурсов используются дополнительные технологии. Например,


  • Helm — генерация манифестов на основе строковых шаблонов + "магазин" готовых компонентов (package manager).
  • Kustomize — ("Kubernetes cUSTOMIZation") — донастройка манифестов путём внесения исправлений в различные свойства.
  • Jsonnet — генерация манифестов с использованием легковесного функционального языка, предназначенного для генерации JSON.

Для синхронизации проектов, хранящихся в репозитории git, с фактическим состоянием инфраструктуры в каком-либо кластере может использоваться специальное приложение, работающее в рамках концепции GitOps, например ArgoCD. Причём поддерживаются как проекты, содержащие собственно манифесты, так и проекты, основанные на вышеперечисленных генераторах/модификаторах.


Эти генераторы широко применяются в различных приложениях и, в целом, позволяют решить задачи, связанные с развёртыванием инфраструктуры. Однако, имеются существенные отличия в подходах, что определяет возможности и потенциальный охват задач.


Рассмотрим, какие требования было бы разумно предъявить к языку описания инфраструктуры. (В этой заметке излагается взгляд автора, занимающегося разработкой программного обеспечения. Другие стороны, например, команды эксплуатации, могут иметь иной взгляд на этот вопрос.)

Читать дальше →

Пишем простой чат с консольным интерфейсом используя трубно-ориентированное программирование с котами

Уровень сложностиПростой
Время на прочтение8 мин
Количество просмотров6.3K

Если в процессе изучения gRPC хотите попрактиковаться с Bidirectional Streaming (двунаправленная потоковая передача данных), c запросами в рамках одного соединения, инициированием событий со стороны сервера, то создание простого чата может быть отличным способом.

Читать далее

Рекурсивное название небольшой статьи о рекурсии

Уровень сложностиСредний
Время на прочтение7 мин
Количество просмотров9.3K

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

Читать далее

Прокачивайте математику – вот как это поможет при программировании

Время на прочтение6 мин
Количество просмотров34K
Пол Орланд исследует, как можно прокачать навыки программирования, развивая математическую подготовку и всё лучше разбираясь в том, как сохраняется связь между математикой и программированием.

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

Концепции Rust, которые неплохо бы знать пораньше

Время на прочтение21 мин
Количество просмотров21K

Весь минувший месяц я глаз не мог оторвать от языка программирования Rust, ведь его конёк – создание современных программ, обеспечивающих безопасную работу с памятью. За прошедшие годы появилось несколько языков, которые позиционировались как «инструмент что надо» для написания надёжного бекенд-софта. Постепенно маятник качнулся от Java/C++ к Go и Rust, выстроенных на многолетних разработках по теории языков программирования. Суть – в создании инструментов, которые были бы эффективны именно в наш век.

Читать далее

Грокаем Traversable

Время на прочтение12 мин
Количество просмотров2.2K

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

Читать далее

История одного соседа

Время на прочтение5 мин
Количество просмотров5.5K

Приветствую всяк смотрящий на моем первом посте на Хабре. Очень долго я шел к тому чтоб решиться написать свой неинтересный рассказ и разместить его тут. И да. это очередной пост о том как кто-то написал скучного бота. Но я получил опыт, который возможно пригодится мне когда-то. Поэтому хотелось бы закрепить. Я расскажу об этапах создания некоторого функционала, идей и с чем я столкнулся и что я узнал не из интернета, а на своём опыте. Возможно кому-то будет полезно.

Однажды, зайдя в чат дома между катками доты, я увидел бота который дает возможность кикать пользователей путем голосования в чате. Нехитрое изобретение, я решил повторить и тогда я впервые познакомился с Telegram Bot API. В частности с библиотекой telebot. И тут первое что хотел бы отметить. На момент написания того самого первого бота, в данной библиотеке использовалась функция polling(), для поддержки бота в сети при простое. Однако она была не идеальной и через буквально 10 минут простоя бот всё же полностью терял соединение и не принимал запросы. На тот момент решением стало вот такая вещь...

Читать далее

Функциональное мышление

Время на прочтение7 мин
Количество просмотров9.8K
imageTL;DR: Конструирование приложения с чистой функцией в основе может стать первым шагом к идеалу «функционально-центричной императивной оболочки», что может упростить тестирование приложения и снизить планку его сложности.
Читать дальше →

Грокаем валидацию при помощи аппликативного функтора

Время на прочтение7 мин
Количество просмотров1.5K

В предыдущем посте мы открыли Аппликативный функтор, а если точнее, изобрели функцию apply. С ее помощью мы решили проблему валидации полей кредитной карты. Функция apply позволила легко объединить результаты каждой функции, отдельно проверяющей одно поле - номер карты, срок действия и CVV - в объект типа Result<CreditCard>, который представляет финальный результат проверки всех данных кредитной карты на корректность. Возможно, вы также помните, что в случае если у нас есть несколько ошибок валидации, мы решили пойти простым путем и просто возвращать первую из них.

Читать далее

Квазицитирование в Lisp

Время на прочтение39 мин
Количество просмотров4.4K

Аннотация


Квазицитирование (quasiquotation) — это технология, обычно используемая в Lisp для создания программ, генерирующих другие программы. В статье объясняется механизм работы квазицитирования, поясняется почему он работает именно так и каковы его ограничения, а также даётся экскурс в историю квазицитирования.

Читать дальше →

Грокаем аппликативные функторы

Время на прочтение8 мин
Количество просмотров5.1K

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

Читать далее

Ближайшие события

SPA потоки и состояния: шаблон Мейоз

Время на прочтение5 мин
Количество просмотров3K

Состояние SPA (одностраничное приложение на javascript) и управление состоянием — бесконечная тема. У всякого популярного js-фрейморка есть пара, тройка решений на этот счет. "Их есть" и без фреймворков и библиотек, с помощью несложной функции и javascript, просто способ управления состоянием (паттерн, шаблон). Автор назвал его Мейоз. Название довольно так себе на мой взгляд, но автору виднее.

Основа паттерна — поток (stream), на удивление простая, но "крутая" идея реактивного функционального программирования. Одной структуры данных и нескольких функций достаточно, чтобы управлять состоянием приложения, не особо "заморачиваясь".

Читать далее

Что же такого прекрасного в функциональном программировании?

Время на прочтение18 мин
Количество просмотров21K

Когда слышишь, как некоторые люди говорят о функциональном программировании, можно подумать, что они попали в какую-то секту. Они болтают о том, как оно изменило их способ восприятия кода. Они превозносят преимущества чистоты. И провозглашают, что теперь они способны «рассуждать о коде», как будто весь остальной код иррационален и непонятен. Этого вполне достаточно, чтобы начать относиться ко всему этому скептически.

Однако вы можете задаться вопросом: должна же быть какая-то причина того, почему эти адепты настолько восхищены? По моему личному опыту, интерес к функциональному программированию обретают не ленивые и некомпетентные программисты. [Один из тех, кому я показал эту статью, прореагировал интересным образом. Он сказал что-то вроде: «Вообще-то я люблю функциональное программирование, потому что я ленивый и компетентный. Благодаря нему мне не приходится думать о многих вещах».] Скорее наоборот, осваивать его были склонны самые умные кодеры, которых я знал; люди, сильнее всех стремившиеся писать хороший код. (Хотя они обычно были исследователями.) И это вызывает вопрос: отчего же они все в таком восторге?
Читать дальше →

Несовершенство трех законов робототехники

Время на прочтение7 мин
Количество просмотров8.9K

Этот диалог не имеет никакого смысла для людей, но он произошел между двумя сетями чат-ботов  ИИ. Назову их условно: Синий кот и Белый кот. Они «делили» предметы: 2 книги, 1 шляпу и 3 шарика. Изначально можно назвать этих котов-ботов junior. В этом эксперименте каждый объект обладал значимостью для сети, выраженной в баллах (от 1 до 3).

Читать далее

Полурешётки и законы Мерфи

Время на прочтение6 мин
Количество просмотров5.4K

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

Читать далее

Core Data в современном интерьере SwftUI. Взаимосвязь объектов. Динамический @FetchRequest. часть 2

Время на прочтение18 мин
Количество просмотров2.7K
В первой части этой статьи мы рассмотрели основы работы с Core Data в SwiftUI на примере шаблонного приложения, предложенное Apple. Это было тривиальное приложение, в котором всего лишь один объект Core Data с одним единственным атрибутом, и тем не менее было показано, что давая объектам Core Data дополнительную функциональность с помощью „синтаксического сахара“ в расширении extension их классов class, автоматически генерируемых Xcode, можно добиться комфортной работы с Core Data в SwiftUI. Эти классы являются миниатюрными ViewModels для наших SwiftUI Views, так как они реализуют протоколы ObservableObject и Identifiable. И Apple научила их прекрасно «играть» на поле реактивности SwiftUI.

Во второй части статьи я хочу показать, что роль автоматически генерируемых Xcode классов class для объектов Core Data существенно возрастает при работе с реальными взаимосвязанными объектами — рейсами Flights, аэропортами Airports и авиакомпаниями AirLines, которые мы получаем в интернете на сайте компании FlightAware и размещаем в локальной базе данных Core Data.

Создаваемое в этой части статьи приложение с именем CoreDataSwiftUIFlights является сильно упрощенной модификацией реального приложения Enroute из стэнфордских курсов CS193P 2020, которое оперативно подкачивает данные с сервера FlightAware и требует от вас платной подписки на сервис FlightAware .

Однако, просто зарегистрировавшись на сайте компании FlightAware, вы можете бесплатно получить временной срез любой интересующей вас информации о рейсах Flights, аэропортах Airports и авиакомпаниях Airlines в JSON формате. Эти данные размещаются в Core Data с учетом взаимосвязей этих объектов, и вы можете не просто видеть всю информацию о рейсах, но и делать различные запросы к ней с помощью фильтров и сортировать ее нужным вам способом.



Код находится на Github.
Читать дальше →

Core Data в современном интерьере SwiftUI. Некоторые уточнения и заблуждения. часть 1

Время на прочтение22 мин
Количество просмотров8.7K
Фреймворк Core Data, разработанный Apple для постоянного хранения данных на своих платформах, эффективно работающий даже с очень большими объемами данных, используется очень давно, с версии iOS 3 и macOs 10.4, так что прошло где-то порядка 10 лет с того момента, когда Apple впервые представила фреймворк Core Data. Когда это произошло, языка программирования Swift вообще не было в проекте, так что Core Data была спроектирована с ориентацией на Objective-C и, конечно, это отразилось на её API.



Но на WWDC 2019 был впервые представлен SwiftUI, который предложил нам новую парадигму конструирования UI, он был предложен для iOS 13 и полностью опирался на Swift, его корни — это Swift, хотя он использует UIKit “под капотом” и полностью зависит от UIKit на iOS, по крайней мере на данный момент, и от AppKit на macOS. Конечно, он это скрывает, как только может, он сконструирован и реализован с прицелом на Swift. Более того, Swift сам был существенно доработан с целью поддержки SwiftUI и стал ещё более мощным и интересным.

Но дело даже не в возрастном различии фреймворков, a в том, что Core Data принципиально связана с объектно-ориентированным программированием ( классы, наследование, делегирование и все такое), a суперсовременный SwiftUI основан на декларативном функциональном программировании (структуры, протокольно-ориентированное программирование) и имеет реактивную природу, которая воплощается в использовании архитектуры MVVM.
Читать дальше →

Дженерики в Go: когда нужны и когда можно без них

Время на прочтение14 мин
Количество просмотров15K

Много раз при обсуждении преимуществ и прелестей Go, как языка разработки, мне приходилось слышать что-то вроде «у вас даже нет дженериков» или «вот завезут дженерики, тогда и поговорим». Так вот, дженерики завезли, давайте посмотрим что из этого вышло. 

Меня зовут Павел Грязнов. Я уже несколько лет пишу на Go в прод, хотя знакомство с языком начал с самых ранних версий. Видел как Garbage Collector мог сделать stop the world на пару секунд, страдал от отсутствия системы зависимостей и других проблем. В этой статье я расскажу о дженериках в Go. Начнём с самых основ, продолжим более продвинутыми примерами и закончим бенчмарками.

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

Читать далее

Вклад авторов