ПрограммированиеiOS разработчик

Опишите особенности паттерна 'Protocol Oriented Programming' в Swift и расскажите, чем он отличается от классического объектно-ориентированного подхода.

Проходите собеседования с ИИ помощником Hintsage

Ответ.

В Swift большой акцент делается на Protocol Oriented Programming (POP). Основная идея POP — проектировать архитектуру, начиная с протоколов (интерфейсов), а не с базовых классов. Протоколы дают гибкость наследования поведения через несколько цепочек, снижая связанность кода.

Swift позволяет протоколам иметь default-реализации (через extensions), что способствует повторному использованию кода без необходимости иерархий классов. Классический ООП опирается на наследование между классами, что ограничено только одной цепочкой наследования. POP свободен от этих ограничений, позволяя композицию и расширяемость.

Код-пример:

protocol Drivable { func drive() } extension Drivable { func drive() { print("Driving forward!") } } struct Car: Drivable {} let car = Car() car.drive() // Выведет: Driving forward!

Вопрос с подвохом.

Можно ли добавить stored property (хранимое свойство) в protocol extension?

Ответ: Нет, в extensions протоколов нельзя добавлять хранимые (stored) свойства, только вычисляемые (computed) свойства и методы. Например,

// Ошибка! extension Drivable { var speed: Int = 0 // Compilation error: Extensions may not contain stored properties }

Примеры реальных ошибок из-за незнания тонкостей темы.


История

В крупном проекте разработчики пытались добавлять хранимые свойства через extensions протоколов для трекинга стейта. Код компилировался с ошибкой, из-за чего пришлось срочно перерабатывать архитектуру в разгар спринта, чтобы использовать сторонние решения с objc_get/setAssociatedObject — что ухудшило читаемость кода.


История

В проекте был реализован базовый класс для разных типов сущностей и использовалось множественное наследование через протоколы. Разработчик перепутал поведение default implementation в extension и попытался переопределить этот метод в struct, ожидая, что будет вызвана именно реализация в struct. В итоге было сложно отследить порядок вызова методов.


История

При масштабировании модуля использовались протоколы для разделения ответственности, но из-за отсутствия опыта с POP, разработчики не обеспечили явные зависимости между протоколами. Это привело к дублированию кода и появлению конфликтов интерфейсов при слиянии нескольких extension на больших командах разработки.