1

我有几个不同的 viewController 需要继承相同的属性,但不是同一类型的 viewController。例如,一个 VC 是常规的 UIViewController,而另一个是 UISplitViewController。我有什么方法可以有效地使用继承来确保它们都具有这些特定属性?还是我只需要给每个人自己单独的声明?

4

4 回答 4

3

您可以使用 上的类别来实现您想要的UIViewController。您可以使用关联对象实现类别中的属性。

有关详细信息,请参阅Objective-C:类别中的属性/实例变量。

于 2013-11-07T22:43:28.850 回答
2

您可以向 UIViewController 添加一个类别。由于 UISplitViewController 继承自 UIViewController,因此它也将具有类别中定义的所有属性和方法。但是,类别有两个限制:

  1. 您不能添加支持实例变量。您可以创建属性,但它们不能有支持它们的实例变量。这意味着如果您覆盖 getter(和 setter,如果是读写),以便它以某种方式读取(或写入)已经存在的属性,那么您很好。如果没有,您可以查看关联对象

  2. 在一个类别中覆盖方法是禁止的。虽然没有什么能阻止您这样做,但如果另一个类别也覆盖了该方法,您将有未定义的行为。你只是不知道哪个方法会被执行。如果你需要重写方法,子类化 UIViewController 会更好。但是,UISplitViewController 将不知道这些属性,除非您也将其子类化并添加相同的属性(在这种情况下,您需要维护这些属性两次)。

于 2013-11-07T22:43:14.767 回答
1

我不确定你到底需要什么。如果您不想(或不能)将公共超类与公共属性一起使用,您可以随时编写协议。唯一的区别是,协议不给你通用的实现,而是强迫你写一个(所以你可以确定它在那里,正如你所要求的那样)。

于 2013-11-07T22:38:36.737 回答
0

为什么不使用共享基类设置继承并在 init 中设置这些共享属性?

//MyBaseVC.h
@interface MyBaseVC : UIViewController
@property (nonatomic, strong) NSString *myString;
@end

//VC1.h
@interface VC1 : MyBaseVC
@end

//VC2.h
@interface VC2 : MyBaseVC
@end

-----

//(MyBaseVC.m)
-(id) init {
    self = [super init];
    if(self){
        self.myString = @"Hello world!";
    } 
    return self;
}

// VC1.m
-(id) init {
    self = [super init];
       NSLog(@"%@", self.myString); // "Hello world!"
    return self;
}

// VC2.m
-(id) init {
    self = [super init];
       NSLog(@"%@", self.myString); // "Hello world!"
    return self;
}

此时,您可以直接引用子类对象上的属性:

NSLog(@"%@",myVc1.myString); //"Hello world!"

否则,当您以更通用的方式引用 VC 时,您始终可以引用它们的超类 (MyBaseVC) - 例如,如果您需要将它们作为方法参数传递。

//-(void)doSomethingWithVC:(MyBaseVC *)vc;
 [someObj doSomethingWithVc: vc1];
于 2013-11-07T22:46:46.263 回答