Вызов TestClass2().test() выбирает наиболее специализированное расширение C2 и печатает C2.
Определение вызываемого метода в иерархии протоколов
Вызов TestClass2().test() выбирает наиболее специализированное расширение C2 и печатает C2.
Короткий ответ
Что ответить на собеседовании
Подробный разбор
Ответ с пояснениями
Условие
В задаче рассматривается ситуация, когда несколько протоколов наследуют друг друга и каждый из них имеет собственную реализацию метода test() в расширении. Нужно понять, какая именно реализация будет выполнена при вызове метода у экземпляра класса, который одновременно соответствует нескольким из этих протоколов.
protocol A2 {
func test()
}
protocol B2: A2 {
func test()
}
protocol C2: B2 {
func test()
}
extension A2 {
func test() {
print("A2")
}
}
extension B2 {
func test() {
print("B2")
}
}
extension C2 {
func test() {
print("C2")
}
}
class TestClass2: A2, C2, B2 {}
TestClass2().test()
Ответ
Вызов TestClass2().test() выбирает наиболее специализированное расширение C2 и печатает C2.
C2 наследует B2, а B2 — A2, поэтому требования образуют цепочку уточнения, а не три независимых конфликтующих протокола. TestClass2 соответствует C2 и тем самым также его предкам. При выборе доступной default-реализации C2 является наиболее конкретным вариантом. Явное перечисление A2 и B2 в объявлении класса здесь избыточно. Не следует переносить этот ответ на несвязанные протоколы с одноимёнными методами: там может возникнуть неоднозначность.