protocol概念及基本使用
1、protocol的基本概念
协议:一些方法的声明,一般写到一个.h的头文件中,供其他的类或者协议去遵守。
在OC中,接口是有一个叫做协议的protocol来实现的。它与java不同的是,它可以声明一些必须实现的方法和选择实现的方法,有选择性的。
2、protocol的使用流程
协议的使用流程:定义协议—》再类中采用指定的协议—》实现协议中对应的方法(选择性的)
1)定义协议
@protocol 协议名称 <NSObject>
//默认遵守NSObject协议
//方法声明列表
@end
2)采用协议
1、类遵守协议
创建类的时候遵守某个或者几个协议
@interface 类名 :父类<协议名称>
@end
@interface 类名 :父类<协议名称1,协议名称2>
@end
2、协议遵守协议
某个协议也遵守某个或者某些协议,一个协议可以遵守其他多个协议,多个协议之间用逗号','隔开
@protocol 协议名称<其他协议名称>
@end
3)实现对应的方法(必须要实现的)
结论:当我们遵守了某个协议后,就相当于这个类有了协议中所有的方法声明
protocol的其他用法
1、protocol的使用注意
1)protocol:就一个用途,用来声明一大堆的方法(不能声明成员变量),不能写实现
2)只要某个类遵守了这个协议,就拥有了这个协议的所有方法声明
3)只要父类遵守某个协议,那么子类也遵守
4)protocol声明的方法可以让任何类去实现,protocol就是协议
5)OC不能继承多个类(单继承),但是可以遵守多个协议。继承(:),遵守协议(<>)
6)基协议:<NSObject>是基协议,是最根本最基本的协议,其中声明了很多最基本的方法
7)协议可以遵守协议,一个协议遵守了另一个协议,就可以拥有另一个协议中的方法声明
2、protocol基协议介绍
NSObject是一个积累,最根本最基本的类,任何其他类最终都要继承它。它还有名字也叫NSObject的协议
,它是一个基协议,最根本最基本的协议。
建议每个新的协议都要遵守NSObject协议。
protocol中@required和@optional
@required和@optional是协议方法声明中的两个关键字
它们主要用于控制方法是否要实现(默认是@required),在大多数情况下,用途在于程序员之间的交流
//必须要实现,不实现编译器报错
//不加关键字,默认是要实现的
@required
-(void)run;
-(void)eat;
//可以实现,也可以不实现
@optional
-(void)run;
-(void)eat;
//可以实现,也可以不实现
@optional
-(void)fight;
protocol类型限制
1、protocol类型限制
1)给id类型增加限制
Girl
*mm = [Girl
new];
//由于id类型可以接受任何类型的对象,要增加类型限制
//id<协议名称>,限制obj,只能赋值遵守了household协议的对象
//由于id类型可以接受任何类型的对象,要增加类型限制
//id<协议名称>,限制obj,只能赋值遵守了household协议的对象
id<houseHoldProtocol> obj = mm;
2)给具体对象增加限制
1、
Girl<houseHoldProtocol> *obj = mm;//在遵守协议的前提下,对象还必须是合理地
2、
@property
(nonatomic,
strong) Dog<suanShuProtocol> *dog;//人拥有会算数的狗,任意的狗就不可以
2、id和instancetype的区别
1)instancetype只能作为函数或者方法的返回值
2)id能作为方法或者函数的返回值、参数类型,也能用来定义变量
3)instancetype对比id的好处:能够精确地限制返回值的具体类型
protocol代理设计模式
代理模式:婴儿和保姆之间有个协议,保姆遵守该协议,于是保姆就需要实现该协议中的条款,从而成为代理人。
错误:linker command failed with exit code 1 (use -v to see invocation)
1)重复包含头文件
2)第三方库
1、protocol代理设计模式概念
MVC模式:m-model(模型) v-view(视图) c-controller(控制器)
代理模式:传入的对象,代替当前类完成了某个功能。
利用协议实现代理模式的主要思路:
1)定义一个协议,里面声明代理类需要实现的方法列表
2)创建一个代理类(比如BaoMu),遵守上面的协议
3)在需要代理的类(Baby)中,定义一个对象,类型为id,且遵守代理协议的成员变量
4)在Baby类中调用成员变量_delegate(代理对象)的方法,调用代理类的方法
5)main.m或其他使用Baby类的文件中,为成员变量赋值
2、protocol代理模式的应用场合
1)当对象A发生了一些行为,想告诉对象B(让对象B称为对象A的代理对象)—》通知场合
2)对象B想监听对象A的一些行为(让对象B称为对象A的代理对象)—》监听器场合
3)当对象A无法处理某些行为的时候,想让对象B帮忙处理(让对象B称为对象A的代理对象)—》自己不想或不能处理
思路实现例子:
1)协议:
#import
<Foundation/Foundation.h>
@class Baby;
@protocol lookBabyProtocol <NSObject>
//喂婴儿吃饭
-(void)feedBabyEat:(Baby *)baby;
//哄婴儿睡觉
-(void)HongBabySleep:(Baby *)baby;
@class Baby;
@protocol lookBabyProtocol <NSObject>
//喂婴儿吃饭
-(void)feedBabyEat:(Baby *)baby;
//哄婴儿睡觉
-(void)HongBabySleep:(Baby *)baby;
@end
2)代理类:
#import
<Foundation/Foundation.h>
//保姆想成为婴儿代理人,必须遵守协议
#import "lookBabyProtocol.h"
@interface BaoMu : NSObject<lookBabyProtocol>
#import "lookBabyProtocol.h"
@interface BaoMu : NSObject<lookBabyProtocol>
@end
#import
"BaoMu.h"
#import "Baby.h"
@implementation BaoMu
//喂婴儿吃饭
-(void)feedBabyEat:(Baby *)baby {
baby.blood += 10;
NSLog(@"保姆正在喂婴儿吃东西!体力值现在为%.2f", baby.blood);
}
//哄婴儿睡觉
-(void)HongBabySleep:(Baby *)baby {
baby.sleep += 20;
NSLog(@"保姆正在哄婴儿睡觉!睡眠值现在为%.2f", baby.sleep);
}
#import "Baby.h"
@implementation BaoMu
//喂婴儿吃饭
-(void)feedBabyEat:(Baby *)baby {
baby.blood += 10;
NSLog(@"保姆正在喂婴儿吃东西!体力值现在为%.2f", baby.blood);
}
//哄婴儿睡觉
-(void)HongBabySleep:(Baby *)baby {
baby.sleep += 20;
NSLog(@"保姆正在哄婴儿睡觉!睡眠值现在为%.2f", baby.sleep);
}
@end
3)需要代理的类:
#import
<Foundation/Foundation.h>
@class
BaoMu;
#import "lookBabyProtocol.h"
@interface Baby : NSObject
#import "lookBabyProtocol.h"
@interface Baby : NSObject
//保姆、体力值、睡眠
@property
(nonatomic,
strong)
BaoMu<lookBabyProtocol> *bm;//此处代理对象一般为_delegate
@property
(nonatomic,
assign)
float
blood;
@property (nonatomic, assign) float sleep;
//吃、睡
-(void)wantEat;
-(void)wantSleep;
@property (nonatomic, assign) float sleep;
//吃、睡
-(void)wantEat;
-(void)wantSleep;
@end
#import
"Baby.h"
#import "BaoMu.h"
@implementation Baby
-(void)wantEat {
NSLog(@"婴儿在哭...");
//保姆要喂他吃
[self.bm feedBabyEat:self];
}
-(void)wantSleep {
NSLog(@"婴儿在哭...");
//保姆要哄她睡
[self.bm HongBabySleep:self];
}
#import "BaoMu.h"
@implementation Baby
-(void)wantEat {
NSLog(@"婴儿在哭...");
//保姆要喂他吃
[self.bm feedBabyEat:self];
}
-(void)wantSleep {
NSLog(@"婴儿在哭...");
//保姆要哄她睡
[self.bm HongBabySleep:self];
}
@end
4)赋值:
#import
<Foundation/Foundation.h>
#import "BaoMu.h"
#import "Baby.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
BaoMu *baomu = [BaoMu new];
Baby *baby = [Baby new];
baby.bm = baomu;
baby.blood = 10;
baby.sleep = 10;
[baby wantEat];
[baby wantSleep];
}
return 0;
#import "BaoMu.h"
#import "Baby.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
BaoMu *baomu = [BaoMu new];
Baby *baby = [Baby new];
baby.bm = baomu;
baby.blood = 10;
baby.sleep = 10;
[baby wantEat];
[baby wantSleep];
}
return 0;
}
引入协议
@protocol 协议名;//类似@class的用法
1、要遵守这个协议的类,用@protocol 告诉编译器这时一个协议
2、在.m文件中,导入协议头文件
3、在main函数中,也要导入协议头文件
本文深入讲解Objective-C中的协议概念,包括基本使用、方法声明、类型限制等,并通过实例介绍了如何利用协议实现代理模式。
735

被折叠的 条评论
为什么被折叠?



