iOS开发中工厂模式的体现

在iOS开发中,简单工厂模式使用得并不多。但是、我认为这是OC反射机制很好的一个例子, 简单工厂模式的实质是由一个工厂类根据传入的参数,动态决定应该创建哪一个产品类(这些产品类继承自一个父类或接口)的实例。该模式中包含的角色及其职责:工厂角色、抽象产品角色、具体产品角色 ——百度百科 简单工厂模式 上面这句话可能不怎么好理解,我在网上找到了一个例子,可能例子本身不能完全解释这个 设计模式的优点,但是它将角色和职责介绍得很清楚: 一个男生想要请女生吃饭,但是这个男生不会做饭。那么干脆就到麦当劳去,让女生自己点喜欢吃的东西就可以了。 在这个例子中,麦当劳就是工厂角色,麦当劳中的产品就是抽象产品角色,薯条、汉堡就是具体产品角色。

引用自【iOS开发系列】用简单工厂模式理解OC反射机制

下面我举一个工程的例子来说明什么是简单的工厂模式: 比如我们的一个APP中的一个页面是用TableViewCell来展示的,但是网络接口中提供的数据是A、B、C三种不同类型的数据,A为纯文字,B为文字+图片,C为纯图片(比如网易新闻,今日头条的首页,只是数据类型比这要复杂得多,而且类型也很多),并且这三种类型的数据是按不规律的形式出现的,那么我们在利用model为cell赋值的时候,cell的展现形式要与model类的数据形式相匹配,这是一件很繁琐的事情,要注册不同类型的的cell用来展现然后再进行类型判断。 工厂模式的原理就是只创建一个model类和cell类,然后以这两个类为父类创建不同的子类,在子类中根据接口数据分配的类型重写model的数据cell的布局等;重写model和cell父类的初始化方法,使用不用的子类的类型来创建父类,总结起来就是一句话:根据不同需求生产不同的产品。

model的父类:
//.h文件
#import <Foundation/Foundation.h>

@interface Model : NSObject

+(instancetype)initWithDictionary:(NSDictionary *)dictionary;

@end

//.m文件
#import "Model.h"
#import "First.h"
#import "Second.h"
#import "Third.h"

@implementation Model


//根据字典内提供的数据分别创建出对应的model来获取数据
+(instancetype)initWithDictionary:(NSDictionary *)dictionary{
    //先使用父类创建对象;
    Model *rootModel = nil;
    
    //根据字典中的key对应的数据初始化不同的子类对象并将其返回给父类
    if ([dictionary[@"tag"] isEqualToString:@"1"]) {
        rootModel = [[First alloc]init];
        
    }else if ([dictionary[@"tag"] isEqualToString:@"2"]){
        rootModel = [[Second alloc]init];
    
    }else if ([dictionary[@"tag"] isEqualToString:@"3"]){
        rootModel = [[Third alloc]init];

    }

    [rootModel setValuesForKeysWithDictionary:dictionary];
    return rootModel;
}

-(void)setValue:(id)value forUndefinedKey:(NSString *)key
{
       
}
@end
复制代码
cell的父类
//.h文件中
#import <UIKit/UIKit.h>
@class Model;

@interface MyTableViewCell : UITableViewCell

//在父类中声明出一个model类对象,在它的子类中重写set方法,在set方法内部去实现赋值操作
@property(nonatomic,strong) Model *model;

//根据不同类型的model创建不同的cell
+(instancetype)initWithModel:(Model *)model;

@end


//.m文件中
#import "MyTableViewCell.h"

@implementation MyTableViewCell

+(instancetype)initWithModel:(Model *)model{

    //根据OC函数获取model类名并将其转化为OC字符串
    NSString *modelName = [NSString stringWithUTF8String:object_getClassName(model)];
    
    //使用model的类名拼接一个"cell"来获取到cell类名
    NSString *cellName = [modelName stringByAppendingString:@"TableViewCell"];
    
    //根据提供的cellName来给予不同cell所对应的'cell子类'初始化一个cell对象返回给我们的父类对象
    
    //唯一标示符可以使我们所提供的model来给与不同cell所对应的标示符来重用
    MyTableViewCell *cell = [[NSClassFromString(cellName) alloc]initWithStyle:(UITableViewCellStyleDefault) reuseIdentifier:modelName];
    return cell;

}
@end
复制代码
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath方法中
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
    
    //根据indexPath.row获取对应的model
    Model *model = [self.dataArray objectAtIndex:indexPath.row];
    
    //根据取出的modle获取对应的类名
    NSString *modelName = [NSString stringWithUTF8String:object_getClassName(model)];
    
    //根据不同的唯一标识重用不同的cell
    MyTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:modelName];
    
    if (cell == nil) {
        //根据我们每行提供的model创建出对应的cell(根据不同的需求生产不同的产品)
        cell = [MyTableViewCell initWithModel:model];
    }
    
    //赋值
    [cell setModel:model];

    return cell;
}
复制代码

工程源代码:Demo 不懂的地方可以留言给我。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值