本节先介绍基于同一工程的分层,根据表10-1所述,基于同一工程的分层可以有:POOO、PSSS、PSOO和POSS模式,比较有代表性的是PSSS、POOO和PSOO,下面简要介绍这3种模式。 10.4.1 采用纯Swift语言实现——PSSS模式 纯Swift语言实现的分层架构如图10-10所示。打开本节案例MyNotes工程,如图10-11所示。在Xcode工程导航面板中,共有3个组——PresentationLayer、BusinessLogicLayer和PersistenceLayer,其中PresentationLayer用于放置表示层相关的类,BusinessLogicLayer用于放置业务逻辑层相关的类,PersistenceLayer用于放置持久层相关的类。 在各个层下面,又是如何划分的呢?我们可以按照业务模块划分,也可以按照组件功能划分。在本应用中,PersistenceLayer层还要分成dao和domain两个组。dao用于放置数据访问对象,该对象中有访问数据的CRUD四类方法。为了降低耦合度,dao一般要设计成为协议(或Java接口),然后根据不同的数据来源采用不同的实现方式。domain组是实体类,实体是应用中的“人”、“事”、“物”等。 图10-10 纯Swift语言实现的分层架构 图10-11 纯Swift语言实现的Xcode工程 提示 CRUD方法是访问数据的4个方法——增加、删除、修改和查询;C为Create,表示增加数据;R是Retrieve,表示查询数据;U是Update,表示修改数据;D是Delete,表示删除数据。 在dao组中,NoteDAO.swift中的代码如下: import Foundation class NoteDAO { //保存数据列表 var listData: NSMutableArray! class var sharedInstance: NoteDAO { struct Static { static var instance: NoteDAO? static var token: dispatch_once_t = 0 } dispatch_once(&Static.token) { Static.instance = NoteDAO() //添加一些测试数据 var dateFormatter : NSDateFormatter = NSDateFormatter() dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss" var date1: NSDate = dateFormatter.dateFromString("2015-01-01 16:01:03")! var note1: Note = Note(date:date1, content: "Welcome to MyNote.") var date2: NSDate = dateFormatter.dateFromString("2015-01-02 8:01:03")! var note2: Note = Note(date:date2, content: "欢迎使用MyNote。") Static.instance?.listData = NSMutableArray() Static.instance?.listData.addObject(note1) Static.instance?.listData.addObject(note2) } return Static.instance! } //插入备忘录的方法 func create(model: Note) -> Int { self.listData.addObject(model) return 0 } //删除备忘录的方法 func remove(model: Note) -> Int { for note in self.listData { var note2 = note as Note //比较日期主键是否相等 if note2.date == model.date { self.listData.removeObject(note2) break } } return 0 } //修改备忘录的方法 func modify(model: Note) -> Int { for note in self.listData { var note2 = note as Note //比较日期主键是否相等 if note2.date == model.date { note2.content = model.content break } } return 0 } //查询所有数据方法 func findAll() -> NSMutableArray { return self.listData } //修改备忘录的方法 func findById(model: Note) -> Note? { for note in self.listData { var note2 = note as Note //比较日期主键是否相等 if note2.date == model.date { return note2 } } return nil } } 在上述代码中,NoteDAO采用了单例设计模式,这种模式与DAO设计模式没有关系,这是为了防止创建多个DAO对象。listData属性用于保存数据表中的数据,其中每一个元素都是Note对象。数据放置在listData属性中(这里本应该是从数据库中取出的,但是数据库访问技术我们还没有学习),CRUD方法也都是对listData而非数据库的处理。 在domain组中,Note的代码如下,它只有两个属性——date是创建备忘录的日期,content是备忘录的内容: import Foundation class Note { var date:NSDate var content:NSString init(date:NSDate, content:NSString ) { self.date = date self.content = content } } 在业务逻辑层BusinessLogicLayer中,类一般是按照业务模块设计的,它的方法是业务处理方法。下面是NoteBL.swift中的代码: import Foundation class NoteBL { //插入备忘录的方法 func createNote(model: Note) -> NSMutableArray { var dao:NoteDAO = NoteDAO.sharedInstance dao.create(model) return dao.findAll() } //删除备忘录的方法 func remove(model: Note) -> NSMutableArray { var dao:NoteDAO = NoteDAO.sharedInstance dao.remove(model) return dao.findAll() } //查询所有数据的方法 func findAll() -> NSMutableArray { var dao:NoteDAO = NoteDAO.sharedInstance return dao.findAll() } } PresentationLayer是表示层,其中的内容大家应该比较熟悉了,这里不再赘述。 10.4.2 采用纯Objective-C语言实现——POOO模式 用纯Objective-C语言实现的分层架构如图10-12所示。打开本节案例MyNotes工程,如图10-13所示。在Xcode工程导航面板中,共有3个组,这类似于图上一节介绍的纯Swift语言实现的工程。 图10-12 使纯Objective-C语言实现的分层架构 图10-13 纯Objective-C语言实现的Xcode工程 下面介绍代码部分。在dao组中,NoteDAO.h的代码如下: @interface NoteDAO : NSObject //保存数据列表 @property (nonatomic,strong) NSMutableArray* listData; + (NoteDAO*)sharedManager; //插入备忘录的方法 -(int) create:(Note*)model; //删除备忘录的方法 -(int) remove:(Note*)model; //修改备忘录的方法 -(int) modify:(Note*)model; //查询所有数据的方法 -(NSMutableArray*) findAll; //按照主键查询数据的方法 -(Note*) findById:(Note*)model; @end 在上述代码中,listData属性用于保存数据表中的数据,其中每一个元素都是Note对象。+ (NoteDAO*) sharedManager方法用于获得NoteDAO单例对象。在dao组中,NoteDAO.m的代码如下: @implementation NoteDAO static NoteDAO *sharedManager = nil; + (NoteDAO*)sharedManager { static dispatch_once_t once; dispatch_once(&once, ^{ NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init]; [dateFormatter setDateFormat:@"yyyy-MM-dd HH:mm:ss"]; NSDate *date1 = [dateFormatter dateFromString:@"2010-08-04 16:01:03"]; Note* note1 = [[Note alloc] init]; note1.date = date1; note1.content = @"Welcome to MyNotes."; NSDate *date2 = [dateFormatter dateFromString:@"2011-12-04 16:01:03"]; Note* note2 = [[Note alloc] init]; note2.date = date2; note2.content = @"欢迎使用MyNotes。"; sharedManager = [[self alloc] init]; sharedManager.listData = [[NSMutableArray alloc] init]; [sharedManager.listData addObject:note1]; [sharedManager.listData addObject:note2]; }); return sharedManager; } //插入备忘录的方法 -(int) create:(Note*)model { [self.listData addObject:model]; return 0; } //删除备忘录的方法 -(int) remove:(Note*)model { for (Note* note in self.listData) { //比较日期主键是否相等 if ([note.date isEqualToDate:model.date]){ [self.listData removeObject: note]; break; } } return 0; } //修改备忘录的方法 -(int) modify:(Note*)model { for (Note* note in self.listData) { //比较日期主键是否相等 if ([note.date isEqualToDate:model.date]){ note.content = model.content; break; } } return 0; } //查询所有数据的方法 -(NSMutableArray*) findAll { return self.listData; } //按照主键查询数据的方法 -(Note*) findById:(Note*)model { for (Note* note in self.listData) { //比较日期主键是否相等 if ([note.date isEqualToDate:model.date]){ return note; } } return nil; } @end NoteDAO也采用了单例设计模式来实现。 在domain组中,Note的代码如下,它只有两个属性——date是创建备忘录的日期,content是备忘录的内容: // //Note.h // #import <Foundation/Foundation.h> @interface Note : NSObject @property(nonatomic, strong) NSDate* date; @property(nonatomic, strong) NSString* content; @end // //Note.m // #import "Note.h" @implementation Note @end 在业务逻辑层BusinessLogicLayer中,NoteBL.h的代码如下: @interface NoteBL : NSObject //插入备忘录的方法 -(NSMutableArray*) createNote:(Note*)model; //删除备忘录的方法 -(NSMutableArray*) remove:(Note*)model; //查询所有数据的方法 -(NSMutableArray*) findAll; @end 下面是NoteBL.m中的代码: @implementation NoteBL //插入备忘录的方法 -(NSMutableArray*) createNote:(Note*)model { NoteDAO *dao = [NoteDAO sharedManager]; [dao create:model]; return [dao findAll]; } //删除备忘录的方法 -(NSMutableArray*) remove:(Note*)model { NoteDAO *dao = [NoteDAO sharedManager]; [dao remove:model]; return [dao findAll]; } //查询所有数据的方法 -(NSMutableArray*) findAll { NoteDAO *dao = [NoteDAO sharedManager]; return [dao findAll]; } @end PresentationLayer是表示层,其中的内容大家应该比较熟悉了,这里不再赘述。 10.4.3 采用Swift与Objective-C混合搭配实现——PSOO模式 Swift与Objective-C混合搭配在目前采用得比较多,这是因为很多老版本的项目还是使用Objective-C开发的。为了最大可能地利用老版本的代码,可以把基于Objective-C编写的业务逻辑层和数据持久层复用。由于iOS每次升级,表示层的API变化都很大,所以表示层一般很难复用,可以采用Swift语言重构。 采用Swift与Objective-C混合搭配的分层架构如图10-14所示。打开本节案例MyNotes工程,如图10-15所示,在Xcode工程导航面板中,共有3个组——PresentationLayer、BusinessLogicLayer和PersistenceLayer, PresentationLayer使用的语言是Swift,BusinessLogicLayer和PersistenceLayer使用的语言是Objective-C。 图10-14 Swift与Objective-C混合搭配实现分层架构 图10-15 Swift与Objective-C混合搭配的Xcode工程 Swift调用Objective-C对象时,需要添加桥接头文件MyNotes-Bridging-Header.h,该文件的内容如下: #import "Note.h" #import "NoteDAO.h" #import "NoteBL.h" 在桥接头文件中引入头文件,是在Swift代码中调用Objective-C对象所需要的头文件。关于具体的调用实现,大家可以参考我们编写的《Swift开发指南》一书。
iOS开发指南 从零基础到App Store上架(第3版)——10.4 基于同一工程的分层
书名: iOS开发指南 从零基础到App Store上架(第3版)
作者: 关东升
出版社: 人民邮电出版社
出版年: 2015-4-1
页数: 658
定价: CNY 99.00
装帧: 平装
ISBN: 9787115387769