import Foundation
    import Swift


    struct HasType<Type: AnyObject> {
        static func inObject<T>(object: T) -> Bool {
            return object is Type
        }
    }


    @objc protocol MyBaseProtocol : class {}
    @objc protocol MyDerivedProtocol : MyBaseProtocol {}
    @objc class MyBaseClass : MyDerivedProtocol {}
    @objc class MyDerivedClass : MyBaseClass {}

    let mbc = MyBaseClass()
    let mdc = MyDerivedClass()

    HasType<MyBaseProtocol>.inObject(mbc) // True
    HasType<MyDerivedProtocol>.inObject(mbc) // True
    HasType<MyBaseProtocol>.inObject(mdc) // False
    HasType<MyDerivedProtocol>.inObject(mdc) // False
    HasType<MyBaseClass>.inObject(mdc) // True
    HasType<MyDerivedClass>.inObject(mdc) // True

Почему этот метод возвращает 2 False. Я ожидаю, что все правда. Что я пропустил? Весь этот код можно было вставить на игровую площадку.

4
knowwis 24 Дек 2014 в 09:14

2 ответа

Лучший ответ

Похоже на ошибку. Задачу можно упростить так:

@objc protocol MyProtocol {}
class MyBaseClass : MyProtocol {}
class MyDerivedClass : MyBaseClass {}

let mbc:AnyObject = MyBaseClass()
let mdc:AnyObject = MyDerivedClass()

mbc is MyProtocol // -> true
mdc is MyProtocol // -> false

Обходной путь - сделать MyBaseClass унаследованным от NSObject

class MyBaseClass : NSObject, MyProtocol { }
                    ^^^^^^^^^^
1
rintaro 24 Дек 2014 в 11:31

Это определенно ошибка. Другой способ обхода, который я нашел, - заставить MyDerivedClass соответствовать MyDeriveProtocol. class MyDerivedClass : MyBaseClass, MyDerivedProtocol {}

import UIKit
import Foundation

struct HasType<Type: AnyObject> {
static func inObject<T>(object: T) -> Bool {
    return object is Type
 }
}
@objc protocol MyBaseProtocol {
func someValue() -> Double
}
@objc protocol MyDerivedProtocol : MyBaseProtocol{}
@objc class MyBaseClass : MyDerivedProtocol {
func someValue() -> Double { return 9.9 }
}
@objc class MyDerivedClass : MyBaseClass, MyDerivedProtocol {}

let mbc = MyBaseClass()
let mdc = MyDerivedClass()
mdc.someValue()

HasType<MyBaseProtocol>.inObject(mbc) // True
HasType<MyDerivedProtocol>.inObject(mbc) // True
HasType<MyBaseProtocol>.inObject(mdc) // true
HasType<MyDerivedProtocol>.inObject(mdc) // true
HasType<MyBaseClass>.inObject(mdc) // True
HasType<MyDerivedClass>.inObject(mdc) // True

Обратите внимание, что вам не придется повторно реализовывать методы и требования MyDerivedProtocol, поскольку об этом уже позаботился MyBaseClass. Это кажется окольным путем.

0
Kalenda 24 Дек 2014 в 17:07