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

Комментарии 16

члены класса

Как-то режет глаз. Хоть я давно и не читал русскоязычной литературы на данную тему, но предпочел бы "свойства" (от property) или "поля".

Тут +, поправлю

Для абстрактных (базовых) классов в Swift есть один хак:

protocol _MyAbstractProtocol {
  func foo()
}

class _MyAbstractClass {
  func bar() {
    if let base = self as? _MyAbstractProtocol {
      base.foo()
    }
  }
}

typealias MyAbstractClass =  MyAbstractClass & _MyAbstractProtocol

class MyConcreteClass: MyAbstractClass {
  func foo() {
    print("foo")
  }
}

Данный способ позволяет уйти от fatalError для базовых методов обязательных к реализации в наследнике, с их контролем на этапе компиляции в виде бонуса.

typealias MyAbstractClass = MyAbstractClass & _MyAbstractProtocol

похоже, тут подчеркивание потеряно? очепятко?

Да, редактор в новом дизайне хабра довольно странный. Должно быть:

typealias MyAbstractClass = _MyAbstractClass & _MyAbstractProtocol

Класс-значение

Вы упустили, что данный вид классов в Swift на 99% заменяется структурами.

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

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

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

Примеры на Swift обязательно добавлю, недочет.

Класс-свойство

Тут вообще непонятно, что вы пытались сказать (как этот термин на английском пишется?), и как его реализовать на Swift.

Это Utility-классы или их еще любят называть Helper-классы. Такие классы очень удобны и их можно встретить в любом проекте. В качестве примера DateUtility.

final class DateUtility {
    
    static func currentDate() -> String {
        ...
    }
    
    static func numberOfDaysInMonth() -> Int {
        ...
    }
    
    static func firstDayOfWeek() -> Int {
        ...
    }
    
    static func dateFor(_ type: DateForType) -> Date {
        ...
    }
    
}

Основная проблема таких классов в том, что они не обладают состояниями, это просто пространство имен, где сгруппированы методы, которые принимают на вход какие-то параметры что-то с ними делают и возвращают данные.

Еще часто замечаю, что утилитные методы любят прятать в extensions к какому либо типу.

Для этих целей в Swift принято использовать enum'ы без case'ов, так как они не имеют инициализатора по-умолчанию и не позволяют наследование.

Еще часто замечаю, что утилитные методы любят прятать в extensions к какому либо типу.

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

Насколько я помню, протоколы в Swift работают аналогично классам в Haskell или трейтам в Rust. Может не стоит натягивать сову на глобус, изображая базовые классы, а начать пользоваться протоколами ?

Верно, для 90% задач протоколов с дефолтной имплементацией должно быть достаточно.

Иногда нужно создать базовый класс на основе библиотечного (например UIViewController ) и тут мой пример с typealias может пригодиться.

Похоже автор не разобрался до конца в Swift и пытается применить паттерны из C++, при том, что последний с трудом можно назвать ООП-языком.

Зарегистрируйтесь на Хабре, чтобы оставить комментарий

Публикации

Истории