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

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

От Lisp до Haskell

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

В Java 21 собираются реализовать сопоставление с образцом – так, глядишь, я снова на этот язык перейду

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

Преуведомление

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

Выпуск Java 21 состоялся 19 сентября 2023 года. В этой версии поддерживаются паттерны записи в switch-блоках и выражениях. Такой синтаксис выглядит монументально (как минимум, по меркам Java). Это водораздел, после которого мы вправе говорить, что в Java полноценно поддерживаются паттерны функционального программирования, подобно тому, как это сделано в Kotlin, Rust или C#. Вот и первый пункт, который пробуждает во мне зависть (я Kotlin-разработчик).

Читать далее
Всего голосов 29: ↑29 и ↓0 +29
Комментарии 12

Вывод оптимального алгоритма с помощью формализма Бёрда-Меертенса

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

Некоторые оптимальные алгоритмы, оказывается, можно вывести из неоптимальных, пользуясь эквивалентными преобразованиями алгоритма. Бёрд и Меертенс разработали формализм, который устанавливает свойства функций высшего порядка map, fold, scan, позволяющие преобразовывать алгоритмы в эквивалентные. (См. также на Вики). Ниже представлен вольный перевод статьи Бёрда.


Рассмотрим задачу поиска максимальной суммы сегмента массива. Эту задачу можно переформулировать в виде математически точного ответа:


Для всех сегментов, которые можно получить из массива, необходимо посчитать сумму чисел, а затем среди всех таких сумм найти максимальную.
Читать дальше →
Всего голосов 11: ↑11 и ↓0 +11
Комментарии 0

Теория типов

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

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

Что можно узнать из этой статьи?
Всего голосов 75: ↑75 и ↓0 +75
Комментарии 70

Ad-hoc-полиморфизм и паттерн type class в C#

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


Эта статья объясняет, что такое ad-hoc-полиморфизм, какие проблемы он решает и как вообще его реализовать, используя паттерн type class на языке программирования C#.
Читать дальше →
Всего голосов 41: ↑40 и ↓1 +39
Комментарии 36

Истории

Бестолковые тесты versus качественное ПО. Часть 3. Что получится?

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

В первой части мы рассмотрели примеры тестов, из которых не все одинаково полезны. Затем попытались определиться, что же такое качество ПО, и предложили "распрямлять" код и выводить программы из требований. Рассмотрели классификацию ошибок. Рассмотрели те задачи, в которых тесты хорошо себя проявляют.


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

Читать дальше →
Всего голосов 4: ↑0 и ↓4 -4
Комментарии 1

Бестолковые тесты versus качественное ПО. Часть 2. Что делать? 5. Применимость юнит-тестов

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

В первой части мы рассмотрели примеры тестов, из которых не все одинаково полезны. Затем попытались определиться, что же такое качество ПО, и предложили "распрямлять" код и выводить программы из требований. Рассмотрели классификацию ошибок.


Видя необоснованные надежды, возлагаемые на юнит-тесты, хотелось бы понять, что в действительности можно ожидать от тестов.

Читать дальше →
Всего голосов 5: ↑0 и ↓5 -5
Комментарии 0

Бестолковые тесты versus качественное ПО. Часть 2. Что делать? 4. Эквивалентность функций

Уровень сложности Сложный
Время на прочтение 14 мин
Количество просмотров 671

В первой части мы рассмотрели примеры тестов, из которых не все одинаково полезны. Затем попытались определиться, что же такое качество ПО, и предложили "распрямлять" код. Рассмотрели классификацию ошибок.


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

Читать дальше →
Всего голосов 7: ↑3 и ↓4 -1
Комментарии 4

Бестолковые тесты versus качественное ПО. Часть 2. Что делать? 3. Ошибки

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

В первой части мы рассмотрели примеры тестов, из которых не все одинаково полезны. Затем попытались определиться, что же такое качество ПО, и предложили "распрямлять" код.


Теперь посмотрим, от каких ошибок защищают тесты, а от каких — другие инструменты из арсенала разработчика.

Читать дальше →
Всего голосов 4: ↑0 и ↓4 -4
Комментарии 0

Бестолковые тесты versus качественное ПО. Часть 2. Что делать? 2. «Распрямляем» код

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

В первой части мы рассмотрели примеры тестов, из которых не все одинаково полезны. Затем попытались определиться, что же такое качество ПО, и как подходить к вопросу тестирования с системной точки зрения.


Теперь рассмотрим один из аспектов разработки, позволяющий уменьшить необходимое количество тестов — "прямолинейность" кода (как понятие, противоположное цикломатической сложности).

Читать дальше →
Всего голосов 5: ↑1 и ↓4 -3
Комментарии 4

Бестолковые тесты versus качественное ПО. Часть 1. Бестолковые тесты

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

Сталкивались с тестами, которые толком ничего не тестируют? А тесты, которые что-то тестируют, но при этом всё равно постоянно возникают баги? Может быть, тесты, которые приходится каждый раз исправлять?


Несложно построить тест, обеспечивающий 100% покрытие, но при этом ничего не проверяющий и не гарантирующий. (См., например).


Проблемы юнит-тестов уже затрагивались на Хабре ранее:



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

Читать дальше →
Всего голосов 10: ↑6 и ↓4 +2
Комментарии 0

Преимущества функционального программирования на примерах C#

Время на прочтение 7 мин
Количество просмотров 7K
Функциональное программирование (ФП) — это парадигма, в которой упор делается на использование функций для решения задач, а не на состояние и изменяемые данные. В последние годы ФП завоевало популярность среди разработчиков благодаря многочисленным преимуществам, которые позволяют использовать его для разработки сложных систем. В этой статье мы расскажем о преимуществах функционального программирования и о том, почему вам стоит рассмотреть возможность его использования в вашем следующем проекте.
Читать дальше →
Всего голосов 16: ↑9 и ↓7 +2
Комментарии 9

Что такое формальная верификация

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

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

Формальная верификация — это доказательство с использованием математических методов корректности программного обеспечения.

Формальная верификация молода. На сегодняшний день, на сайте хабр, например, нет (пока) специализации «Формальная верификация», нет специальности «Proof инженер» или «Специалист по формальной верификации». А люди, работающие по этой специальности — есть.

Программное обеспечение, которое прошло формальную верификацию считается надежным. Формальная верификация дает (с математической точностью) гарантии того, что программный код не будет содержать конкретных ошибок, что функции будут вести себя так, как ожидается.

В основе формальной верификации лежат математические методы. Слово «формальный» в названии - это отсылка к математике. Для доказательства утверждений о программном коде используются формальные методы математики: математическая логика, лямбда исчисление, теория категорий, математический анализ, алгоритмы для работы с функциональными и императивными структурами данных.

Инструменты для верификации — это программные средства для доказательства теорем (Coq, Isabelle ...), а также SAT-solvers.

В 70х годах предки формальной верификации — это доказательства простых утверждений о программе (конкретной функции) с помощью ручки и листка бумаги. Сегодня — это (иногда многолетние) исследовательские проекты для конкретного программного обеспечения, вот некоторые из них:

Читать далее
Всего голосов 17: ↑17 и ↓0 +17
Комментарии 27

Python кодогенерация — ускоряем strftime / strptime

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

Привет! В первой и второй частях я поделился историей создания python библиотеки convtools (кратко: позволяет декларативно описывать преобразования данных, из которых генерируются python функции, реализующие заданные преобразования), сейчас расскажу об ускорении частных случаев datetime.strptime и datetime.strftime, а также о том интересном, что встретилось в datetime модуле по дороге.

Читать далее
Всего голосов 4: ↑4 и ↓0 +4
Комментарии 0

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

PG Bootcamp 2024
Дата 16 апреля
Время 09:30 – 21:00
Место
Минск Онлайн
EvaConf 2024
Дата 16 апреля
Время 11:00 – 16:00
Место
Москва Онлайн
Weekend Offer в AliExpress
Дата 20 – 21 апреля
Время 10:00 – 20:00
Место
Онлайн

Парсер комбинаторы на Python

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

Статья предлагает взглянуть на опыт разработки парсер комбинаторов для Python, что вылилось в библиотеку PGPC для разработки парсеров на Python. Библиотека была вдохновлена Parsec.
Особый интерес представляет эмуляция do-нотации через Python генераторы, отсюда и название библиотеки: Python Generator based Parser Combinator library.

Читать далее
Всего голосов 2: ↑2 и ↓0 +2
Комментарии 13

Верификация рекурсивных функций в Coq. Проблема остановки. Горючее

Уровень сложности Сложный
Время на прочтение 5 мин
Количество просмотров 1.5K

Статья предполагает, что читатель имеет опыт работы с интерактивным программным средством доказательства теорем — Coq.

Статья является адаптированной русскоязычной версией моей статьи, написанной во время работы над формальной верификацией протокола криптовалюты Tezos.

В данной статье мы рассмотрим прием, который используется для работы с рекурсивными функциями, которые не проходят проверку завершаемости (тотальности) в Coq. Под «горючим» мы будем понимать натуральное число, которое вводится как дополнительный параметр в тело функции, чтобы обозначить верхнюю границу числа итераций, которые функция может совершить. Таким образом функция трансформируется в завершаемую, удобную для работы, и радушно принимаемую компилятором Coq. В литературе термин встречается под названиями: petrol, fuel, gas и т.д.

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

Это значит Coq не может определить какой аргумент на каждом шаге итерации будет уменьшаться. Можно попробовать явно указать Coq на аргумент, который, мы точно знаем будет уменьшаться на каждом шаге {struct уменьшаемый_аргумент}:

Читать далее
Всего голосов 3: ↑3 и ↓0 +3
Комментарии 5

COQ: верификация функций, содержащих fold_left

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

Данная статья является адаптированной русскоязычной версией моей статьи: Handling fold_left in proofs.

Функция fold_left , сворачивающая список, довольно популярна во многих (функциональных и не очень) языках программирования. Она есть и в Haskell, и в OCaml и в Rust. Используется чаще, чем fold_right, вероятно потому, что с ее помощью проще писать эффективный код.

fold_left и fold_right из библиотеки OCaml library: List.

Читать далее
Всего голосов 7: ↑7 и ↓0 +7
Комментарии 20

Формальная верификация кода на Coq: тактики

Уровень сложности Сложный
Время на прочтение 4 мин
Количество просмотров 999

Данная статья является адаптированным переводом моей статьи: Formalization of code in Coq - tactics, написанной в период работы над проектом coq-tezos-of-ocaml.

Суть проекта: часть исходного кода протокола криптовалюты Tezos была переведена на Coq, а затем верифицирована с помощью математических методов и формальной логики.

Статья предназначена для круга читателей, имеющих опыт работы с Coq.

Часто процесс формальной верификации становится утомительным и монотонным из за повторяющихся действий, которые пруф-инженеру (от английского слова proof - доказательство) приходится выполнять. К счастью, в Coq есть инструменты и техники автоматизации доказательств, которые позволяют не только значительно увеличить производительность, но и сделать доказательства короче.

В данной статье мы покажем, как использовать и писать тактики на примере формальной верификации исходного кода криптовалюты Tezos (написанной на OCaml), а именно, мы затронем следующие темы:

Читать далее
Всего голосов 10: ↑8 и ↓2 +6
Комментарии 4

Применение формулы бинома для определения простых чисел

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

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

Читать далее
Всего голосов 9: ↑6 и ↓3 +3
Комментарии 24

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

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

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

Читать далее
Всего голосов 13: ↑10 и ↓3 +7
Комментарии 11

Разработка расширяемого алгоритма строкового калькулятора

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

В данной статье рассматривается создание расширяемого алгоритма строкового калькулятора, который позволяет пользователю самостоятельно определять операции и константы, с которыми работает калькулятор. Основная цель статьи - предоставить описание процесса разработки и реализации такого алгоритма, а также продемонстрировать его гибкость и возможности для настройки под индивидуальные нужды пользователей.

Читать далее
Всего голосов 4: ↑4 и ↓0 +4
Комментарии 11