2016-01-28 9 views
2

У меня есть два класса, которые я хочу использовать в своем новом классе. Первый реализует салфетки, чтобы удалить и второй дает длинный пресс жест:Способ наследования от нескольких классов

class DeleteItem: UITableViewCell { 
} 

class OpenDetail: UITableViewCell { 
} 

Поскольку Swift не позволяет классу наследовать от нескольких классов в следующем примере, очевидно, не будет работать:

class ItemViewCell: DeleteItem, OpenDetail { 
} 

Так что для того, чтобы создать ItemViewCell и иметь оба варианта, я должен иметь один из классов наследовать друг от друга:

class DeleteItem: UITableViewCell { 
} 

class OpenDetail: DeleteItem { 
} 

class ItemViewCell: OpenDetail { 
} 

проблема заключается в том, если мне нужен только длинный жест нажатия, мне придется создать новый класс без наследования с DeleteItem. Есть ли лучший способ сделать это?

+0

[Да] (https://developer.apple.com/library/ios/documentation/Swift/Conceptual/Swift_Programming_Language/Extensions.html). – SmokeDispenser

+0

@JanGreve: Не возражаете ли вы показать мне пример того, как достичь этого, используя расширения? В моем проекте это дает мне ошибку. – Laap

+1

Не можете ли вы сделать 'DeleteItem' и' OpenDetail' протоколы, а не классы? –

ответ

4

Это идеальный вариант для использования протоколов и расширения протокола. Быстрое похоже на интерфейс в Java, например. Протокол может определять набор функций, которые должны быть реализованы объектами, которые хотят соответствовать этому протоколу, причем протокол может определять свойства, которые также должны присутствовать в этих объектах. Например:

protocol ItemDeleter { 
    var deletedCount: Int {get set} 
    func deleteItem(item: ItemType) 
} 

Проблема заключается в том, что каждая организация будет иметь, чтобы обеспечить свою собственную реализацию func deleteItem(item: ItemType) даже если несколько лиц одни и те же логику удаления элемента, это когда расширение протокола пригождается. Например:

extension ItemDeleter { 
    func deleteItem(item: ItemType) { 
    // logic needed to delete an item 

    // maybe incremented deletedCount too 
    deletedCount++ 
    } 
} 

Тогда вы могли бы сделать ваш ItemViewCell соответствовать протоколу ItemDeleter, в этом случае все, что вам нужно, чтобы убедиться, что ItemViewCell имеет свойство deletedCount: Int. Не нужно предоставлять реализацию для func deleteItem(item: ItemType), поскольку сам протокол предоставляет реализацию по умолчанию для этой функции, однако вы можете переопределить ее в своем классе, и будет использоваться новая реализация. То же самое относится к DetailOpener protocol.

+1

Нет, протоколы не могут дать вам многократное наследование. Особенно, когда обе реализации пытаются переопределить один и тот же метод. – Sulthan

+0

@Sulthan, протоколы могут дать вам представление о множественном наследовании. В случае наличия двух реализаций по умолчанию для одного и того же метода, требуемого в двух разных протоколах, компилятор будет жаловаться на то, что вы не соответствуете протоколу, который вы соответствовали последнему, и потребует, чтобы вы предоставили свою собственную реализацию, чтобы функция соответствовала обеим протоколам , Я считаю, что подклассы здесь не являются хорошим дизайном. – ysholqamy

+0

Проблема в том, что протоколы не подходят для этого точного случая. Это не сработает. – Sulthan

Смежные вопросы