Каковы уровни абстракции, описанные в книге 'Чистый код' Роберта Мартина?

Я читаю книгу "Чистый код" Роберта Мартина и столкнулся с понятием уровней абстракции в третьей главе, посвященной функциям. Мне не совсем понятно, что подразумевается под уровнями абстракции и как тут помогают TO-абзацы. 

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

Однако, в книге приводится следующий пример кода:
<pre><code class="java">public Money calculatePay(Employee e)
throws InvalidEmployeeType {
    switch (e.type) {
      case COMMISSIONED:
        return calculateCommissionedPay(e);
      case HOURLY:
        return calculateHourlyPay(e);
      case SALARIED:
        return calculateSalariedPay(e);
      default:
        throw new InvalidEmployeeType(e.type);
    }
  }</code></pre> 
В книге утверждается, что эта функция "совершенно очевидно выполняет более одной операции", но мне это не очевидно. Из-за этой главы я не могу продвинуться дальше в чтении, и очень прошу объяснить простыми словами, что собой представляют уровни абстракции и как их можно выделять?
  • 9 декабря 2024 г. 8:23
Ответы на вопрос 2
Уровни абстракции в контексте книги "Чистый код" Роберта Мартина относят к тому, как организована логика в коде и как она представлена. Каждый уровень абстракции представляет собой степень общего представления о выполняемых задачах, и они помогают сделать код более читаемым и поддерживаемым.

1. **Высший уровень абстракции** — это тот уровень, на котором описывается, что делает функция в контексте бизнес-логики. Это может быть, например, название функции `calculatePay`, которое указывает на то, что функция выполняет расчет зарплаты работника. Здесь мы рассматриваем функциональность с точки зрения пользователя или бизнес-логики, не углубляясь в детали реализации.

2. **Низший уровень абстракции** — это детали того, как именно реализуется задача. В данном случае, это различные алгоритмы, используемые для расчета зарплаты в зависимости от типа работника (например, `calculateCommissionedPay`, `calculateHourlyPay`, `calculateSalariedPay`). Здесь вы уже будете иметь дело с конкретными операциями (расчетами), которые выполняются для получения результата.

Теперь о **TO-абзацах**, которые упоминаются в книге. TO-абзацы представляют собой блоки кода, которые служат для ясной структуризации. Например, если вы смотрите на функцию `calculatePay`, можете выделить в ней абстракции:

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

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

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

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

Например:
Первый уровень - драйверы базы данных. Они реализуют соединение с базой, протокол обмена данными.
Второй - универсальный интерфейс базы данных (PDO). Он реализует работу с любой базой данных в едином стиле.
Третий - ORM. Он представляет объектную модель данных, хранящихся в БД.
Четвёртый - основные операции бизнес-логики.
Пятый - бизнес-логика верхнего уровня.

При этом, драйвер БД использует сетевой интерфейс, у которого семь уровней абстракции (модель OSI), не вдаваясь в детали реализации.
Похожие вопросы