1

Императивный и декларативный код

Всем привет, работаю java разработчиком 10 лет, хотел бы показать разницу между императивным и декларативным подходом на примере синтетической задачи по обработке списка чисел.

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

Задан список чисел, на примере:

List<Integer> input = List.of(1, 2, 3, 4, 5);

Нужно найти сумму квадратов чётных чисел - значений элементов массива. Чётные числа это такие числа, которые делятся нацело на 2, то есть остаток от деления числа на два равен нулю. Чётные числа здесь 2 и 4. Их квадраты это 4 и 16. Искомая сумма 4 + 16 = 20.

Чтобы записать алгоритм в императивном подходе, потребуется объявить переменную-аккумулятор, которая будет содержать сумму, её начальное значение будет 0. Далее пройтись по всем элементам списка, для четных их них посчитать квадрат, и добавить его к текущему значению суммы:

int sumEven = 0;

for (Integer x : input) { //пройти по всем элементам

__ if (x % 2 == 0) { //для четных

____ sumEven += x * x; //посчитать квадрат и добавить к сумме

__ }

}

assertEquals(sumEven, 20);

Декларативный подход можно показать на примере использования апи java.util.stream. Последовательно указываются инструкции для фильтрации, преобразования и аккумуляции результата:

int sumEven = input.stream()
__ .filter(x -> x % 2 == 0)
__ .map(x -> x * x)
__ .reduce(0, Integer::sum);
assertEquals(sumEven, 20);

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

Лига программистов

2K поста11.8K подписчиков

Правила сообщества

- Будьте взаимовежливы, аргументируйте критику

- Приветствуются любые посты по тематике программирования

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

3
Автор поста оценил этот комментарий

Исходя из ваших определений, второй пример тоже императивный, просто выполняется с помощью других принципов, работы со всем списком, а не с каждым элементом.
Он описывает именно "последовательность действий с использованием конструкций языка".
Если это декларация, то тогда i=i+1 тоже декларация, только на одном элементе.
И написание+использование функции "возвести каждый элемент в квадрат и вернуть новый список" - тоже декларация.
Пример состоит из императивов:
"отсеять нечетные елементы",

"возвести в квадрат каждый элемент списка",

"сложить все члены списка"

Только последняя строка как-то напоминает декларацию, но она даже не часть алгоритма, а часть необезательная часть тестирования.

раскрыть ветку (1)
Автор поста оценил этот комментарий

<enabled>true</enabled> - это декларация или уже императивное выражение? Между ними тяжело провести грань, особенно когда в силу сложности модели для конфигурации фреймворка требуется использовать свой отдельный язык конфигурации.

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

показать ответы
1
Автор поста оценил этот комментарий

1. Опасно для квадратов интов использовать инт.

2. А что про эффективность и скорость? Простой цикл выглядит производительнее...

раскрыть ветку (1)
Автор поста оценил этот комментарий

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

Декларативными могут быть не только алгоритмы расчета - например, сборщик кода maven это чисто декларативный фреймворк, использует xml для конфигурации.