类簇

作者: 程序狗 | 来源:发表于2023-04-18 19:21 被阅读0次

    类簇是一种设计模式,就是公共抽象父类对多个私有的具体子类进行分组,以这种方式对类进行分组简化了面对对象框架的公共可见体系结构,是基于抽象工厂设计模式设计的。
    什么是抽象工厂模式。
    工厂模式属于创建型模式,可以分为简单工厂模式、工厂模式和抽象工厂模式
    简单工厂模式:根据传入的参数返回不同的实例


    image.png

    工厂模式: 让一个类的实例化延迟到子类,即factory类由子类实现,一个对象对应一个factory子类


    image.png
    抽象工厂模式:提供一个创建一系列相关或者互相依赖对象的接口,而无需指定它们具体的类。(在抽象工厂里面,每一个具体工厂都提供了多个工程方法用于产生不同类型的对象)
    image.png

    工厂模式的好处
    1.解耦,创建的代码和使用分开
    2.代码复用,简化实例化代码
    3.容易扩展或修改

    以NSArray举例

    id obj1 = [NSArray alloc];        //__NSPlaceholderArray
    id obj2 = [NSMutableArray alloc]; //__NSPlaceholderArray
    id obj3 = [obj1 init];            //__NSArray0
    id obj4 = [obj2 init];            //__NSArrayM
    

    alloc 之后NSArray和NSMutableArray 都是生成__NSPlaceholderArray对象,然后init方法中生成__NSArray0和__NSArrayM的具体子类。在这个过程中__NSPlaceholderArray可以理解为是一个抽象工厂,而init则是抽象工厂的子类实例化过程
    要实现这个过程,肯定会有个变量去存储它是由哪个类alloc出来,然后在init过程中根据这个变量来生成对应的子类

    static __NSPlaceholderArray *GetPlaceholderForNSArray() {
        static __NSPlaceholderArray *instanceForNSArray;
        if (!instanceForNSArray) {
            instanceForNSArray = [__NPlaceholderArray alloc];
        }
        return instanceForNSArray;
    }
    
    static __NSPlaceholderArray *GetPlaceholderForNSMutableArray() {
        static __NSPlaceholderArray *instanceForNSMutableArray;
        if (! instanceForNSMutableArray) {
            instanceForNSMutableArray = [__NPlaceholderArray init];
        }
        return instanceForNSMutableArray;
    }
    
    //NSArray实现  
    +(id)alloc {
        if(self == [NSArray class]) {
            return GetPlaceholderForNSArray;
        } else {
            return [super alloc]; 
        }
    }
    
    //NSMutableArray实现  
    +(id)alloc {
        if(self == [NSMutableArray class]) {
            return GetPlaceholderForNSMutableArray;
        } else {
            return [super alloc]; 
        }
    }
    
    //__NSPlaceholderArray 实现  
    -(id)init {
        if (self == GetPlaceholderForNSArray) {
            self = [[__NSArray0 alloc] init];
        } else if (self == GetPlaceholderForNSMutableArray) {
            self = [[__NSArrayM alloc] init];
        } else {
            self = [super init];
        }
        return self;
    }
    

    验证可以用以下代码

      for (NSInteger i = 0; i< 10; i++) {
            NSLog(@"%p",[NSMutableArray alloc]);
        }
        for (NSInteger i = 0; i< 10; i++) {
            NSLog(@"%p",[NSArray alloc]);
        }
    

    所以我们在做集合类的安全气垫处理时,需要通过反射拿对应的子类。例如

    Class __NSArrayM = NSClassFromString(@"__NSArrayM");
    

    相关文章

      网友评论

          本文标题:类簇

          本文链接:https://www.haomeiwen.com/subject/gwsuddtx.html