赞
踩
设计模式是指在特定上下文中解决常见问题时所采用的一套可复用的解决方案。这些模式是面向对象编程中的通用概念,广泛应用于各种编程语言和平台。设计模式能够帮助开发者编写更加高效、可读性强、易于维护的代码。它们通常分为三大类:创建型模式、结构型模式和行为型模式。工厂模式属于创建型模式,这类模式关注于对象的创建过程,提供了创建对象的不同方式,以降低耦合度并提高代码的灵活性。
这类模式关注于对象的创建过程,提供了创建对象的不同方式,以降低耦合度并提高代码的灵活性。
这类模式关注于如何组合类和对象以获得更大的结构,同时保持结构的灵活和高效。
这类模式关注于对象间的通信,以及职责的分配。
每个类或者模块应该有且只有一个改变的理由。也就是说,一个类应当专注于做好一件事情,这样可以提高类的内聚性,减少耦合。
比如:UIView负责事件的传递、响应,CALayer负责视图的显示、动画,他们各自都有自己的单一职责。
软件实体(类、模块、函数等)应该对扩展开放,对修改关闭。这意味着当需要改变行为时,应该通过扩展而不是修改已有的代码来实现。
里氏替换原则
子类应当能够替换它们的基类并且不影响程序的正确性。换言之,使用基类的地方能够无差别地使用子类对象。
依赖倒置原则
高层模块不应依赖于低层模块,二者都应该依赖于抽象。抽象不应该依赖于细节,细节应该依赖于抽象。
接口隔离原则
客户端不应该被迫依赖它不需要的接口。接口应该尽量细化,避免臃肿的接口定义,客户端只依赖它实际需要的方法。
迪米特法则/ 最小知识原则
一个对象应当对其他对象有最少的了解。一个类应该只和它的朋友通信,不要和朋友的朋友通信,以减少耦合。
合成/聚合复用原则
尽量使用对象组合而非类继承来达到复用的目的。组合使得系统更加灵活,容易扩展和维护。
合成
合成是指一个总体对依托他而存在的关系,如一个人对他的房子和家具。该关系依赖性不强,比如人没了,这个关系就自然消失了。
聚合
聚合是比合成关系更强的一种依赖关系,如有一台汽车,汽车对引擎、轮胎的关系就是聚合关系。这些关系就是带有聚合性质的。车没了,该车的引擎和轮胎自然也没了。在我们的设计中,这种关系不应该频繁出现,因为这样会增大设计的耦合度。
明确了合成和聚合关系,再来理解合成复用原则应该就清楚了:我们要尽量找出应用中可能需要变化之处,把它们独立出来,不要和那些不需要变化的代码混在一起。
简单工厂模式(Simple Factory Pattern)是一种常用的设计模式,它属于创建型模式的一种。这种模式旨在为创建对象提供一个统一的接口,隐藏了创建对象的具体逻辑,使得客户端不需要知道所创建对象的具体类,从而降低了对象之间的耦合度,提高了代码的灵活性和可维护性。
专门定义一个类(工厂类)来负责创建其他类的实例。可以根据创建方法的参数来返回不同类的实例,被创建的实例通常具有共同的父类。(总结来说就是把一大堆if-else判断由业务层放到工厂类里面)。
优点
缺点
主要作用
通过引入工厂类,使对象的创建和使用分离了。这样的好处是它们可以独立的变化,易维护和扩展。
客户端依赖抽象基类(接口),而不是具体的类,降低了耦合度。
文件分类
通过传递进来的字符串来确定生成的类:
//CYZActionFactory.h #import <Foundation/Foundation.h> NS_ASSUME_NONNULL_BEGIN @interface CYZActionFactory : NSObject +(id)createAction:(NSString*)actionType; @end NS_ASSUME_NONNULL_END //CYZActionFactory.m #import "CYZActionFactory.h" #import "CYZWork.h" #import "CYZPlay.h" #import "CYZStudy.h" @implementation CYZActionFactory +(id)createAction:(NSString *)actionType { if ([actionType isEqualToString:@"work"]) { return [[CYZWork alloc] init]; } else if([actionType isEqualToString:@"play"]) { return [[CYZPlay alloc] init]; } else { return [[CYZStudy alloc] init];; } } @end
其中通过工厂类返回的各种类(各种行为)必须遵守以下协议:
@protocol AcitonFactoryDelegate <NSObject>
- (void)actionSelect;
@end
在各类中实现此方法:
// CYZWork.m
#import "CYZWork.h"
@implementation CYZWork
- (void)actionSelect {
[self work];
}
- (void)work {
NSLog(@"I love work!");
}
@end
运行结果如下:
简单工厂方法和类族模式主要区别就是,类族模式实现各子类方法通过继承去重写父类方法,而简单工厂方法中生成的各类和工厂类并不是父子类关系,通过协议来完成各方法。
工厂方法模式(Factory Method Pattern)是iOS开发中一种常用的设计模式,属于创建型模式的一种。它为创建对象提供了一种灵活的方式,让子类来决定实例化哪一个类,从而实现了对象创建的延迟化和抽象化,增强了代码的扩展性和可维护性。
定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法使得一个类的实例化延迟到了子类。就像Cocoa Touch中的NSNumber的numberWithBool和numberWithInt方法,他们传入不同类型的参数,获得NSNumber实例。
优点
和直接创建具体对象相比,使用工厂方法创建对象算是最佳的做法。
根据所需产品找对应工厂进行生产,不关心产品细节,也不需要知道产品类的类名。
当系统中加入新产品时,不需要修改抽象工厂和抽象产品提供的接口,也无须修改客户端和其他的具体工厂和具体产品,而只要添加一个具体工厂和与其对应的具体产品就可以了,符合了“开-闭”原则。
缺点
当系统中加入新产品时,除了需要提供新的产品类之外,还要提供与其对应的具体工厂类。因此系统中类的个数将成对增加,增加了系统的复杂度。
主要作用:
编译时无法准确预期需要创建对象的类。
类想要其子类决定在运行时创建什么类型的实例。
类有若干辅助类为其子类,而你想将返回哪个子类这种信息局部化。
工厂类中并没有类方法,只有一些方法,简单工厂方法是通过协议的方法去令其他类完成方法,而工厂方法模式是通过继承,令其他类继承工厂类,去重写父类的这几个方法,下面是代码:
文件分类
工厂类:
//FactoryMethodClass.h #import <Foundation/Foundation.h> NS_ASSUME_NONNULL_BEGIN @interface FactoryMethodClass : NSObject - (void)createAction; @end NS_ASSUME_NONNULL_END //FactoryMethodClass.m #import "FactoryMethodClass.h" @implementation FactoryMethodClass - (void)createAction { NSLog(@"action"); } @end
子类:
//CYZWork.h #import <Foundation/Foundation.h> #import "FactoryMethodClass.h" NS_ASSUME_NONNULL_BEGIN @interface CYZWork : FactoryMethodClass @end NS_ASSUME_NONNULL_END /CYZWork.m #import "CYZWork.h" @implementation CYZWork - (void)createAction { [self createWork]; } - (void)createWork { NSLog(@"I love work"); } @end
在viewController中初始化时以父类编译,子类运行
if ([button.titleLabel.text isEqualToString:@"work"]) {
FactoryMethodClass* object = [[CYZWork alloc] init];
[object createAction];
} else if ([button.titleLabel.text isEqualToString:@"play"]) {
FactoryMethodClass* object = [[CYZPlay alloc] init];
[object createAction];
} else {
FactoryMethodClass* object = [[CYZStudy alloc] init];
[object createAction];
}
运行结果如下:
抽象工厂方法(Abstract Factory Method)是设计模式中的一个概念,它属于创建型模式。抽象工厂模式是对简单工厂模式的进一步扩展,它提供了一种创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。与简单工厂模式相比,抽象工厂模式可以生成多个产品族,每个族内有一系列相关的产品。
工厂方法模式只有一个抽象产品类,而抽象工厂模式有多个抽象产品类。抽象工厂模式里每个工厂都会生产多种产品,但不同工厂生产的产品属于不同的系列。抽象工厂模式可以用来解决多产品族的问题。
优点
缺点
主要作用:
文件分类
首先Manager相当于最大的工厂类,通过这个类里的函数来确定是哪个工厂,apple厂还是banana厂:
//FactoryManager.h #import <Foundation/Foundation.h> #import "BaseFactory.h" NS_ASSUME_NONNULL_BEGIN typedef NS_ENUM(NSInteger, CYFactoryType) { CYApple, CYBanana }; @interface FactoryManager : NSObject + (id)factoryWithType:(CYFactoryType)factoryType; @end NS_ASSUME_NONNULL_END //FactoryManager.m #import "FactoryManager.h" #import "AppleFactory.h" #import "BananaFactory.h" @implementation FactoryManager + (id)factoryWithType:(CYFactoryType)factoryType { if (factoryType == CYApple) { return [[AppleFactory alloc] init]; } else if (factoryType == CYBanana) { return [[BananaFactory alloc] init];; } return nil; } @end
接下来到了工厂这步:
首先有一个作为两家工厂的父类,两家工厂继承于此类,并重写此基础类的各方法,以此来展示不同的效果:
父类工厂:
//BaseFactory.h #import <Foundation/Foundation.h> #import "BasePhone.h" #import "BasePad.h" NS_ASSUME_NONNULL_BEGIN @interface BaseFactory : NSObject - (BasePhone*)createPhone; - (BasePad*)createPad; @end NS_ASSUME_NONNULL_END //BaseFatcory.m #import "BaseFactory.h" @implementation BaseFactory - (BasePhone*)createPhone { return nil; } - (BasePad*)createPad { return nil; } @end
子类工厂:
//AppleFactory.h #import <Foundation/Foundation.h> #import "BaseFactory.h" NS_ASSUME_NONNULL_BEGIN @interface AppleFactory : BaseFactory @end NS_ASSUME_NONNULL_END //AppleFactory.m #import "AppleFactory.h" #import "ApplePhone.h" #import "ApplePad.h" @implementation AppleFactory - (BasePhone*)createPhone { return [[ApplePhone alloc] init]; } - (BasePad*)createPad { return [[ApplePad alloc] init]; } @end
//BananaFactory.h #import <Foundation/Foundation.h> #import "BaseFactory.h" NS_ASSUME_NONNULL_BEGIN @interface BananaFactory : BaseFactory @end NS_ASSUME_NONNULL_END //BananaFactory.m #import "BananaFactory.h" #import "BananaPhone.h" #import "BananaPad.h" @implementation BananaFactory - (BasePhone*)createPhone { return [[BananaPhone alloc] init]; } - (BasePad*)createPad { return [[BananaPad alloc] init]; } @end
在下面的一步我们让apple和banana厂分别可以生产手机和平板两种产品,这时候和上一步一样,有一个基础手机类和基础平板类:
基础手机类:
//BasePhone.h #import <Foundation/Foundation.h> NS_ASSUME_NONNULL_BEGIN @interface BasePhone : NSObject - (void)phoneCell; @end NS_ASSUME_NONNULL_END //BasePhone.m #import "BasePhone.h" @implementation BasePhone - (void)phoneCell { NSLog(@"This is a Phone"); } @end
苹果手机类:
//ApplePhone.h #import <Foundation/Foundation.h> #import "BasePhone.h" NS_ASSUME_NONNULL_BEGIN @interface ApplePhone : BasePhone @end NS_ASSUME_NONNULL_END //ApplePhone.m #import "ApplePhone.h" @implementation ApplePhone - (void)phoneCell { NSLog(@"This is an applePhone"); } @end
香蕉手机类:
//BananaPhone.h #import <Foundation/Foundation.h> #import "BasePhone.h" NS_ASSUME_NONNULL_BEGIN @interface BananaPhone : BasePhone @end NS_ASSUME_NONNULL_END //BananaPhone.m #import "BananaPhone.h" @implementation BananaPhone - (void)phoneCell { NSLog(@"This is a bananaPhone"); } @end
平板类和上面相似这里就不再赘述
下面是ViewContrroller类
#import "ViewController.h" #import "FactoryManager.h" #import "ApplePhone.h" #import "AppleFactory.h" #import "ApplePad.h" #import "BananaFactory.h" #import "BananaPhone.h" #import "BananaPad.h" @interface ViewController () @end @implementation ViewController - (void)viewDidLoad { [super viewDidLoad]; // Do any additional setup after loading the view. BaseFactory *appleFactory = [FactoryManager factoryWithType:CYApple]; ApplePhone* applePhone = (ApplePhone*)[appleFactory createPhone]; [applePhone phoneCell]; ApplePad* applePad = (ApplePad*)[appleFactory createPad]; [applePad padCell]; NSLog(@"-------------------------------------"); BaseFactory *bananaFactory = [FactoryManager factoryWithType:CYBanana]; BananaPhone *bananaPhone = (BananaPhone*)[bananaFactory createPhone]; [bananaPhone phoneCell]; BananaPad* bananaPad = (BananaPad*)[bananaFactory createPad]; [bananaPad padCell]; }
运行结果如下:
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。