如何在几个自定义类上实现Objective-C Category

时间:2012-06-02 06:59:52

标签: objective-c

我有几个UIViewController的子类,我想使用一个类别来为它们提供所有方法。问题是我只希望我的类不是基类UIViewController才能拥有那些类别方法。

说我有:

PanelAViewController
PanelBViewController
...

我想实现并回应课程:

PanelAnimations

-(void)animateIn;
-(void)animateOut;

我可以使用协议并且每次都插入方法,但是它们使用相同的方法和值,所以类别不适合吗?

我只是不确定如何定义这些自定义类的类别。

3 个答案:

答案 0 :(得分:2)

似乎你最好的选择是从UIViewController派生一个自定义类,称之为“MyUIViewControllerBase”。将自定义方法添加到该类,然后从中派生其余视图控制器。不需要任何类别,它可以解决您的问题。

答案 1 :(得分:2)

为什么你不考虑子类化,而不是使用类别或协议?在这里,您可以简单地创建一个AbstractViewController类(从UIViewController中删除),该类定义面板动画方法,然后从抽象方法派生您自己的具体控制器(PanelAViewController,PanelBViewController等)。

抽象类将定义方法并最终定义实现中的一些存根(如果您希望PanelA和PanelB应调用super,则由您决定)。这取决于您想要给抽象类的抽象程度。请参阅下面的代码示例。

有时候不清楚使用协议或子类或委托机制是否更好。大多数时候边界不清楚,最终的决定更多地依赖于程序员的偏好而不是“编纂”的架构规则。通常,当您希望不同的对象具有某些特定任务的共同行为时,您会使用协议(例如:您有一组复杂的实体,其中一个实体应该用作地图注释:在这种情况下,您必须简单地提供此特定实体MKAnnotation协议兼容性);委托主要用于扩展类而不进行子类化或者不给最终用户子类化的可能性。在您的情况下,我认为子类化是最合适的选择,因为所有类都严格地属于同一个类层次结构,它们共享一个公共代码(或通用接口)并为每个类提供专门的实现。



//
//  AbstractViewController.h
//

#import 

@interface AbstractViewController : UIViewController

-(void)doAnimate;
-(void)didAnimate;

@end

//
//  AbstractViewController.m
//

#import "AbstractViewController.h"

@interface AbstractViewController ()

@end

@implementation AbstractViewController


-(void)doAnimate {
    NSLog(@"Abstract do animate");
}

-(void)didAnimate {
    NSLog(@"Abstract did animate");
}

//
//  ConcreteViewController.h
//

#import "AbstractViewController.h"

@interface ConcreteViewController : AbstractViewController

@end

//
//  ConcreteViewController.m
//

#import "ConcreteViewController.h"

@interface ConcreteViewController ()

@end

@implementation ConcreteViewController


-(void)doAnimate {
    [super doAnimate];
    NSLog(@"Subclass do animate");
}

答案 2 :(得分:1)

假设您可以控制所有自定义ViewControllers,最简单的方法是创建NSViewController的子类 - 如MyViewController - 并从中继承您自己的ViewControllers的每个子类。这样你甚至不必为它们写一个类别。您可以在MyViewController

中简单地实现所需功能
          NSViewController
                 |
          MyViewController -- implement your shared methods here
           /           \
MyViewControllerA  MyViewControllerB