一、单例设计模式

  1、应用场景:  程序运行期间,在内存中只有一个实例存在,主要用于资源共享,对硬件的访问等等

  2、优点:    跨模块,解耦合,使用简单

  3、敏捷原则:  单一职责原则

  4、SDK实例:

  • UIApplication类提供了 +sharedAPplication方法创建和获取UIApplication单例
  • NSBundle类提供了 +mainBunle方法获取NSBundle单例
  • NSFileManager类提供了 +defaultManager方法创建和获得NSFileManager单例。(PS:有些时候我们得放弃使用单例模式,使用-init方法去实现一个新的实例,比如使用委托时)
  • NSNotificationCenter提供了 +defaultCenter方法创建和获取NSNotificationCenter单例(PS:该类还遵循了另一个重要的设计模式:观察者模式)
  • NSUserDefaults类提供了 +defaultUserDefaults方法去创建和获取NSUserDefaults单例

  5、自定义实例:使用宏定义快速实现单例设计模式

        1、项目中增加一个Singleton.h文件

        2、编辑新增加的Singleton.h文件,添加如下代码

 // .h
 #define single_interface(class)  + (class *)shared##class;

 // .m
 // \ 代表下一行也属于宏
 // ## 是分隔符
 #define single_implementation(class) \
 static class *_instance; \
  \
 + (class *)shared##class \
 { \
     if (_instance == nil) { \
         _instance = [[self alloc] init]; \
     } \
     return _instance; \
 } \
  \
 + (id)allocWithZone:(NSZone *)zone \
 { \
     static dispatch_once_t onceToken; \
     dispatch_once(&onceToken, ^{ \
         _instance = [super allocWithZone:zone]; \
     }); \
     if (_instance == nil) { \
     _instance = [super allocWithZone:zone]; \
     } \
     return _instance; \
 }

         3、自己需要实现一个单例的时候,只需要在.h文件中添加声明:single_interface(dataBaseManager);在.m文件中添加实现:single_implementation(dataBaseManager)就可以了。参考下面代码的实现:

单例对象头文件:

 //
 //  SingleTest.h
 //  XXX
 //
 //  Created by wushukai on 15/7/8.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import <Foundation/Foundation.h>
 #import "Singleton.h"               // 包含单例实现的宏定义的头文件

 @interface SingleTest : NSObject
 single_interface(SingleTest)        // 声明该单例
 @property (nonatomic, strong) NSString *MyName;
 @end

单例对象源文件:

 //
 //  SingleTest.m
 //  XXX
 //
 //  Created by wushukai on 15/7/8.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import "SingleTest.h"

 @implementation SingleTest

 single_implementation(SingleTest)   // 实现该单例
 -(id)init                           // 在init里面初始化该单例的相关数据
 {
     self = [super init];
     if (self)
     {
         self.MyName = @"我是一个单例";
     }
     return self;
 }
 @end

单例调用者头文件:

 //
 //  callSingleTest.h
 //  XXX
 //
 //  Created by wushukai on 15/7/8.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import <Foundation/Foundation.h>

 @interface callSingleTest : NSObject

 @end

单例调用者源文件:

 //
 //  callSingleTest.m
 //  XXX
 //
 //  Created by wushukai on 15/7/8.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import "callSingleTest.h"
 #import "SingleTest.h"              // 调用的时候,包含单例的头文件

 @implementation callSingleTest

 -(id)init
 {
     self = [super init];
     if (self)
     {
         SingleTest *ST = [SingleTest sharedSingleTest];     // 现在就可以使用单例对象了
         NSLog(@"ST的名字 = %@", ST.MyName);
     }
     return self;
 }
 @end

二、代理设计模式

  1、应用场景:  这种模式用于一个对象“代表”另外一个对象和程序中的其他对象进行交互。当一个类的某些功能需要别人来实现的时候,但是既不明确是些什么功能,也不明确到底由谁来实现,委托代理模式就派上用场了。

  2、优点:    使类之间的耦合性更松散。好的代码应该开放扩展关闭修改

  3、敏捷原则:  开放-封闭原则

  4、cocoa框架中的delegate设计模式:

         UITableView常用代理方法:前三个为UITableViewDataSource协议代理方法,剩下的为UITableViewDelegate协议代理方法

 #pragma mark -  1、设置分组
 - (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView

 #pragma mark -  2、设置每个组有多少行共有多少行
 - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section

 #pragma mark -  3、设置UITableViewCell的内容
 -(UITableViewCell*)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

 #pragma mark -  4、设置每个UITableViewCell的行高
 - (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath

 #pragma mark -  5、设置accessory的点击响应事件
 - (void)tableView:(UITableView *)tableView accessoryButtonTappedForRowWithIndexPath:(NSIndexPath *)indexPath

 #pragma mark - 6、返回每组头标题名称
 - (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section;

 #pragma mark - 7、返回每组尾部说明
 - (NSString *)tableView:(UITableView *)tableView titleForFooterInSection:(NSInteger)section;

 #pragma mark - 8、设置分组页头的高度
 -(CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section;

 #pragma mark - 9、设置分组页脚的高度
 - (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section;

 #pragma mark - 10、将要选中了某一行
 -(NSIndexPath*)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath;

 #pragma mark - 11、确实选中了某一行
 -(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath;

 #pragma mark - 12、设置划动cell是否出现del按钮,可供删除数据里进行处理
 -(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath;

 #pragma mark - 13、设置cell是否可以上下移动
 -(BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath;

         UIScrollView常用的代理方法:

 // 1、返回一个放大或者缩小的视图
 - (UIView *)viewForZoomingInScrollView:(UIScrollView *)scrollView;

 // 2、开始放大或者缩小
 - (void)scrollViewWillBeginZooming:(UIScrollView *)scrollView withView:(UIView *)view;

 // 3、缩放结束时
 - (void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(UIView *)view atScale:(float)scale;

 // 4、视图已经放大或缩小
 - (void)scrollViewDidZoom:(UIScrollView *)scrollView;

 // 5、是否支持滑动至顶部
 - (BOOL)scrollViewShouldScrollToTop:(UIScrollView *)scrollView;

 // 6、滑动到顶部时调用该方法
 - (void)scrollViewDidScrollToTop:(UIScrollView *)scrollView;

 // 7、scrollView 已经滑动
 - (void)scrollViewDidScroll:(UIScrollView *)scrollView;

 // 8、scrollView 开始拖动
 - (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView;

 // 9、scrollView 结束拖动
 - (void)scrollViewDidEndDragging:(UIScrollView *)scrollView willDecelerate:(BOOL)decelerate;

 // 10、scrollView 开始减速(以下两个方法注意与以上两个方法加以区别)
 - (void)scrollViewWillBeginDecelerating:(UIScrollView *)scrollView;

 // 11、scrollview 减速停止
 - (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView;

         UITextField常用代理方法:

 #pragma mark -  在用户每次输入的时候都会调用,返回YES代表允许输入
 - (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string;

 #pragma mark -  在文本框准备聚焦的时候调用,返回NO代表不允许聚焦(编辑)
 - (BOOL)textFieldShouldBeginEditing:(UITextField *)textField;

 #pragma mark -  当文本框开始获得焦点的时候调用
 - (void)textFieldDidBeginEditing:(UITextField *)textField;

 #pragma mark -  在文本框准备失去焦点(退出键盘)的时候调用,返回YES代表允许退出键盘
 - (BOOL)textFieldShouldEndEditing:(UITextField *)textField;

 #pragma mark -  当用户失去焦点的时候调用
 - (void)textFieldDidEndEditing:(UITextField *)textField;

        UIPickerView常用代理方法:

 #pragma mark - 数据源方法
 #pragma mark - 有多少列
 - (NSInteger)numberOfComponentsInPickerView:(UIPickerView *)pickerView;

 #pragma mark - 第component列有多少行
 - (NSInteger)pickerView:(UIPickerView *)pickerView numberOfRowsInComponent:(NSInteger)component;

 #pragma mark - 每行显示什么内容、第component列第row行显示什么文字
 - (NSString *)pickerView:(UIPickerView *)pickerView titleForRow:(NSInteger)row forComponent:(NSInteger)component;

 #pragma mark - 代理方法
 #pragma mark - 手动选中了某一行
 - (void)pickerView:(UIPickerView *)pickerView didSelectRow:(NSInteger)row inComponent:(NSInteger)component;

        UIImagePickerController常用代理方法:

 #pragma mark - 选中了图片或者视频之后调用
 - (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info;
  5、自定义代理:顾客饿了,但是不自己做饭,委托餐馆做饭

    代理定义方:顾客
      头文件:
 //
 //  Client.h
 //  basefoundationTest
 //
 //  Created by wushukai on 15/7/9.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import <Foundation/Foundation.h>

 @protocol ClientDelegate <NSObject>

 -(void)hungry;

 @end

 @interface Client : NSObject

 @property(assign, nonatomic) id clientDelegate;     // 代理对象

 @end

      源文件:

 //
 //  Client.m
 //  basefoundationTest
 //
 //  Created by wushukai on 15/7/9.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import "Client.h"

 @implementation Client

 @end

    代理实现方:餐馆

      头文件:

 //
 //  Server.h
 //  basefoundationTest
 //
 //  Created by wushukai on 15/7/9.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import <Foundation/Foundation.h>

 @interface Server : NSObject

 @end

      源文件:

 //
 //  Server.m
 //  basefoundationTest
 //
 //  Created by wushukai on 15/7/9.
 //  Copyright (c) 2015年 mzk. All rights reserved.
 //

 #import "Server.h"
 #import "Client.h"

 #pragma mark - 遵守代理协议
 @interface Server()<ClientDelegate>

 @end

 @implementation Server

 -(id)init
 {
     self = [super init];
     if (self)
     {
         Client *client = [[Client alloc] init];
         client.clientDelegate = self;               // 1、设置当前顾客的代理目的地
         [client.clientDelegate hungry];             // 2、顾客饿了,通知服务员点餐
     }
     return self;
 }

 #pragma mark - 实现顾客的代理方法
 -(void)hungry
 {
     NSLog(@"你饿了,要吃饭,我帮你做");
 }

 @end

三:MVC设计模式

  如下图所示:

  

  1、简介:是一中非常古老的设计模式,通过数据模型,控制器逻辑,视图展示将应用程序进行逻辑划分。

  2、组成:MVCModel(模型)-- View(视图)-- Controller(控制器)。 下面通过使用UITableView显示城市列表来解释。   

     M(模型):  (city)为列表中显示的城市名字提供数据
     V(视图):  (UITableView)将city模型中的数据展示出来让用户可以看见并且交互
     C(控制器): (UITableViewController)控制视图的创建和销毁,显示和隐藏,处理用户与视图的事件交互

    1、V通常通过两种方式与C交互:

                  1、Delegate,比如UITableViewDataSource和UITableViewDelegate;

                  2、Target-action,比如用户在视图上点击了某一个按钮

    2、M一般通过两种方式与C交互:

                  1、Notification;在控制器中注册通知,需要触发的时候,在模型中发送通知

                  2、KVO;键值对改变通知观察者,在控制器中观察模型数据的变化

    3、C一般通过M暴露出来的APIM进行读写操作,比如用户在视图中修改了某个城市的名字,则通过控制器间接修改模型数据

    4、C一般通过OutletV进行交互

     5、VM之间不进行直接交互,使用C作为中介进行交互

  3、优势:使系统层次分明,职责独立,易于维护

   4、敏捷原则:对扩展开放,对修改封闭

四:观察者模式

  1、简介:被观察者对象状态改变,通知正在对他进行观察的观察者对象,观察者对象根据各自要求做出相应的改变

   2、优势:解耦合

  3、敏捷原则: 接口隔离原则,开放扩展,封闭修改

  4、实例:cocoa框架中的观察者设计模式实例

    1、Notification(通知中心)。任何地方可以发送消息,注册观察者的地方可以接收。

    2、KVO(key-value-observer)。键值对改变通知观察者。

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

ios项目总结一:开发中常用的设计模式的更多相关文章

  1. iOS开发中常用的设计模式

    常用的设计模式(一)代理模式应用场景:当一个类的某些功能需要由别的类来实现,但是又不确定具体会是哪个类实现.优势:解耦合敏捷原则:开放-封闭原则实例:tableview的 数据源delegate,通过 ...

  2. Android开发中常用的设计模式

    首先需要说明的是,这篇博文灵感来自于 http://www.cnblogs.com/qianxudetianxia/archive/2011/07/29/2121547.html ,在这里,博主已经很 ...

  3. 根据数据库的表生成项目,项目变为hibernate项目(实际开发中常用)

    1.  选择模式为Myeclipse Database Explorer perpective 2. (1)右键建立mysql模板,选择默认的mysql模板 (2)drive name (任意这里取m ...

  4. Java开发中常用的设计模式(二)---单例模式

    一. 懒汉式单例 //懒汉式单例类.在第一次调用的时候实例化自己 public class Singleton { private Singleton() {} private static Sing ...

  5. Java开发中常用的设计模式(一)---工厂模式

    一. 准备工作 1. 本文参考自  自己理解的工厂模式,希望对大家有所帮助 二. 开始 以汽车工厂为例,首先有个汽车类的接口 Car,里面有个开车的方法 drive(),然后有个宝马车的类 BMW 和 ...

  6. Java开发中常用的设计模式(三)---建造者模式

    一. 模式结构 建造者模式主要包含四个角色: Product:产品角色. Builder:抽象建造者.它声明为创建一个Product对象的各个部件指定的抽象接口. ConcreteBuilder:具体 ...

  7. iOS开发中常用的数学函数

    iOS开发中常用的数学函数 /*---- 常用数学公式 ----*/ //指数运算 3^2 3^3 NSLog(,)); //result 9 NSLog(,)); //result 27 //开平方 ...

  8. .net开发中常用的第三方组件

    .net开发中常用的第三方组件 2013-05-09 09:33:32|  分类: dotnet |举报 |字号 订阅     下载LOFTER 我的照片书  |   RSS.NET.dll RSS. ...

  9. Java开发中常用jar包整理及使用

    本文整理了我自己在Java开发中常用的jar包以及常用的API记录. <!-- https://mvnrepository.com/artifact/org.apache.commons/com ...

随机推荐

  1. OpenERP在哪储存附件?

    我们知道对OpenERP中的每个内部对象(比如:业务伙伴,采购订单,销售订单,发货单,等等)我们都可以添加任意的附件,如图片,文档,视频等.那么这些附件在OpenERP内部是如何管理的呢? 默认情况下 ...

  2. scroll、offset和client的区别

    整体布局: <!DOCTYPE> <head> <meta http-equiv="Content-Type" content="text/ ...

  3. JS 比较日期相隔都少天&& 比较两个日期大小&&指定日期往前后推指定天数

    //这些天常接触到有关于js操作日期事 就小结了一下,希望对你有帮助 function conversionDate(a,b){ var start =a.split('-'); var end = ...

  4. MarkMan – 马克鳗,让设计更有爱!

    scavin(Google+) on 2010.11.16. MarkMan – 马克鳗 是一款方便高效的标注工具,极大节省设计师在设计稿上添加和修改标注的时间,让设计更有爱.Adobe AIR 平台 ...

  5. BootStrap 模态框基本用法

    <!DOCTYPE html> <html> <head> <title>Bootstrap 实例 - 模态框(Modal)插件方法</title ...

  6. centos下安装php后连接不上mysql

    安装完php后需要安装php的扩展比如: 安装php的扩展yum install php-mysql php-gd php-imap php-ldap php-odbc php-pear php-xm ...

  7. super()和this()的区别

    1)调用super()必须写在子类构造方法的第一行,否则编译不通过.每个子类构造方法的第一条语句,都是隐含地调用super(),如果父类没有这种形式的构造函数,那么在编译的时候就会报错. 2)supe ...

  8. php课程---语句及函数

    语句:    一:分支语句        1.if(条件1){满足条件1执行}    2.if(条件1){满足条件1执行}else{不满足条件1执行}    3.if(条件1){满足条件1执行}els ...

  9. Python2.x和3.x主要差异总结

    本文部分转载自http://my.oschina.net/chihz/blog/123437,部分来自自身修改 开始使用Python之后就到处宣扬Python如何如何好,宣传工作的一大重要诀窍就是做对 ...

  10. String-自定义功能

    <script> /* *发现js中的String对象有限,想要对字符串操作的其他功能. *比如:去除字符串两端的空格.这时只能自.定义 */ //去除字符串两端的空格 function ...