iOS开发基础-KVC简单介绍
一、KVC介绍
键值编码(Key Value Coding,KVC):使开发者不必进行任何操作就可以进行属性的动态读写。
KVC操作方法由 NSKeyValueCoding 协议提供,而 NSObject 实现了这个协议,因此 ObjC 中几乎所有的对象都支持KVC操作,常用的操作方法如下:
1)动态设置: setValue:forKey: 用于简单路径, setValue:forKeyPath: 用于复合路径。如 Person 类有一个 Account 类型的属性,那么 Person.Account 就是一个复合属性。
2)动态读取: valueForKey: 、 valueForKeyPath: 。
补充:键值观察(Key Value Observer,KVO):监听某一个模型的属性,只要该模型属性的值发生变化就通知你。
二、代码实例1
新建 Command Line Tool 项目,并命名为 KVCDemo 。紧接着,为项目添加一个继承自 NSObject 类的 Person 类,为该新类添加名字和年龄属性,如下:
//Person.h
@property (nonatomic, copy) NSString *name;
@property (nonatomic, assign) int age;
在 Person 类的实现文件中重写 description 方法:
//Person.m
- (NSString *)description {
return [NSString stringWithFormat:@"<%@:%p>, {name:%@, age:%d}.", [self class], self, self.name, self.age];
}
上述中 %p 指代指针。
在 main.m 文件中对 Person 进行简单的处理:
//main.m
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *p1 = [[Person alloc] init];
[p1 setValue:@"WJQ" forKey:@"name"];
[p1 setValue:@"" forKey:@"age"]; Person *p2 = [[Person alloc] init];
[p2 setValue:@"LWX" forKey:@"name"];
[p2 setValue:@"" forKey:@"age"];
NSLog(@"%@. %@.", p1, [p2 valueForKey:@"name"]);
}
return ;
}
使用 setValue:forKey: 进行KVC操作时,系统会自动判断对象属性的类型并完成转换,如上例将 @"" 转换为 。
输出为:
<Person:0x1006001c0>, {name:WJQ, age:}.. LWX.
三、代码实例2
如何生成只包含 name 属性的数组,并打印出来?
在 main.m 文件中中导入 Person 类的头文件,并修改 main 函数的代码:
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *p1 = [[Person alloc] init];
[p1 setValue:@"WJQ" forKey:@"name"];
[p1 setValue:@"" forKey:@"age"]; Person *p2 = [[Person alloc] init];
[p2 setValue:@"LWX" forKey:@"name"];
[p2 setValue:@"" forKey:@"age"]; NSArray *persons = @[p1, p2]; //创建Person对象的数组
NSLog(@"%@", persons);
NSMutableArray *arrayM = [NSMutableArray array]; //用于存放各个Person的name
for (Person *p in persons) {
[arrayM addObject:[p valueForKeyPath:@"name"]];
}
NSLog(@"%@", arrayM);
}
return ;
}
输出为:
(
"<Person:0x100208dc0>, {name:WJQ, age:23}.",
"<Person:0x100209c80>, {name:LWX, age:22}."
)
(
WJQ,
LWX
)
由于使用KVC按键值路径取值时,如果对象不包含指定的键值,会自动进入对象内部,查找对象的属性。在不改变输出的情况下,修改上述代码为:
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *p1 = [[Person alloc] init];
[p1 setValue:@"WJQ" forKey:@"name"];
[p1 setValue:@"" forKey:@"age"]; Person *p2 = [[Person alloc] init];
[p2 setValue:@"LWX" forKey:@"name"];
[p2 setValue:@"" forKey:@"age"]; NSArray *persons = @[p1, p2]; //创建Person对象的数组
NSLog(@"%@", persons);
NSMutableArray *arrayM = [NSMutableArray array]; //用于存放各个Person的name
[arrayM addObject:[persons valueForKeyPath:@"name"]];
NSLog(@"%@", arrayM);
}
return ;
}
三、代码实例3
演示根据键值路径取值,KVC机制会自动层层深入,并获取对应的键值。
为项目新建一个 Book 类继承自 NSObject ,添加 bookName 属性:
//Book.h
@property(nonatomic, copy) NSString *bookName;
修改 Book 类的 description 方法:
//Book.m
- (NSString *)description {
return [NSString stringWithFormat:@"<%@, %p>, {bookName:%@}", [self class], self, self.bookName];
}
接着在 Person 类的头文件中导入 Book.h ,再添加一个 Book 类的对象属性,如下:
//Person.h
@property (nonatomic, strong) Book *book;
修改 Person 类的 description 方法,使其输出 book 属性:
//Person.m
- (NSString *)description {
return [NSString stringWithFormat:@"<%@:%p>, {name:%@, age:%d, book:%@}.", [self class], self, self.name, self.age, self.book];
}
最后,修改 main 函数:
//main.m
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *p1 = [[Person alloc] init];
[p1 setValue:@"WJQ" forKey:@"name"];
[p1 setValue:@"" forKey:@"age"];
Book *b1 = [[Book alloc] init];
b1.bookName = @"iPhone";
p1.book = b1; Person *p2 = [[Person alloc] init];
[p2 setValue:@"LWX" forKey:@"name"];
[p2 setValue:@"" forKey:@"age"];
Book *b2 = [[Book alloc] init];
b2.bookName = @"iOS";
p2.book = b2; NSArray *persons = @[p1, p2]; //创建Person对象的数组
NSLog(@"%@", persons);
NSArray *arrayM = [persons valueForKeyPath:@"book.bookName"];
NSLog(@"%@", arrayM);
}
return ;
}
输出为:
(
"<Person:0x1002095d0>, {name:WJQ, age:23, book:<Book, 0x10020c4c0>, {bookName:iPhone}}.",
"<Person:0x10020c520>, {name:LWX, age:22, book:<Book, 0x10020c540>, {bookName:iOS}}."
)
(
iPhone,
iOS
)
参考博客:ios开发UI篇—Kvc简单介绍
实例代码:http://pan.baidu.com/s/1dDYZAOL
iOS开发基础-KVC简单介绍的更多相关文章
- iOS开发网络篇—简单介绍ASI框架的使用
iOS开发网络篇—简单介绍ASI框架的使用 说明:本文主要介绍网络编程中常用框架ASI的简单使用. 一.ASI简单介绍 ASI:全称是ASIHTTPRequest,外号“HTTP终结者”,功能十分强大 ...
- iOS开发UI篇—简单介绍静态单元格的使用
iOS开发UI篇—简单介绍静态单元格的使用 一.实现效果与说明 说明:观察上面的展示效果,可以发现整个界面是由一个tableview来展示的,上面的数据都是固定的,且几乎不会改变. 要完成上面的效果, ...
- iOS开发Swift篇—简单介绍
iOS开发Swift篇—简单介绍 一.简介 Swift是苹果于2014年WWDC(苹果开发者大会)发布的全新编程语言 Swift在天朝译为“雨燕”,是它的LOGO 是一只燕子,跟Objective-C ...
- 【iOS开发】NSOperation简单介绍
iOS开发多线程篇—NSOperation简单介绍 一.NSOperation简介 1.简单说明 NSOperation的作⽤:配合使用NSOperation和NSOperationQueue也能实现 ...
- iOS开发UI篇—Kvc简单介绍
ios开发UI篇—Kvc简单介绍 一.KVC简单介绍 KVC key valued coding 键值编码 KVC通过键值间接编码 补充: 与KVC相对的时KVO,即key valued observ ...
- IOS开发基础知识碎片-导航
1:IOS开发基础知识--碎片1 a:NSString与NSInteger的互换 b:Objective-c中集合里面不能存放基础类型,比如int string float等,只能把它们转化成对象才可 ...
- iOS开发基础-九宫格坐标(3)之Xib
延续iOS开发基础-九宫格坐标(2)的内容,对其进行部分修改. 本部分采用 Xib 文件来创建用于显示图片的 UIView 对象. 一.简单介绍 Xib 和 storyboard 的比较: 1) X ...
- iOS开发基础-九宫格坐标(2)之模型
在iOS开发基础-九宫格(1)中,属性变量 apps 是从plist文件中加载数据的,在 viewDidLoad 方法中的第20行.26行中,直接通过字典的键名来获取相应的信息,使得 ViewCont ...
- iOS开发多线程篇—GCD介绍
iOS开发多线程篇—GCD介绍 一.简单介绍 1.什么是GCD? 全称是Grand Central Dispatch,可译为“牛逼的中枢调度器” 纯C语言,提供了非常多强大的函数 2.GCD的优势 G ...
随机推荐
- selenium和webdriver区别
接触selenium大概半年时间了.从开始的预研,简单的写个流程到后期的自动化框架的开发,因为本人不属于代码方面的大牛,一直的边研究边做.逐步深入学习.近期发现自己对本身selenium的发展还存在困 ...
- Docker 网络之进阶篇
笔者在<Docker 基础 : 网络配置>一文中简单介绍了容器网络的基本用法,当时网络的基本使用方式还处于 --link 阶段.时过境迁,随着 docker 的快速发展,其网络架构也在不断 ...
- Jenkins持续集成01—Jenkins服务搭建和部署
一.介绍Jenkins 1.Jenkins概念 Jenkins是一个功能强大的应用程序,允许持续集成和持续交付项目,无论用的是什么平台.这是一个免费的源代码,可以处理任何类型的构建或持续集成.集成Je ...
- springmvc 项目完整示例08 前台页面以及知识点总结
至此已经基本测试成功了,我们稍作完善,让它成为一个更加完整的项目 我们现在重新规划下逻辑 两个页面 一个登录页面 一个欢迎页面 登陆页面输入账号密码,登陆成功的话,跳转登陆成功 欢迎页面 并且,更新用 ...
- Perl一行式:选择行输出、删除、追加、插入
perl一行式程序系列文章:Perl一行式 对于Perl的一行式perl程序来说,选择要输出的.要删除的.要插入/追加的行是非常容易的事情,因为print/say决定行是否输出/插入/追加/删除.虽然 ...
- Redis的复制是如何实现的?
前言 关系数据库通常会使用一个主服务器向多个从服务器发送更新,并使用从服务器来处理所有的读请求,Redis采用了同样方法来实现自己的复制特性. 简单总结起来就是:在接收到主服务器发送的数据初始副本之后 ...
- 常见MQTT服务器搭建[转载]
简介 MQTT(Message Queuing Telemetry Transport,消息队列遥测传输)是IBM开发的一个即时通讯协议,它比较适合于在低带宽.不可靠的网络的进行远程传感器和控制设备通 ...
- 深入浅出Java类加载过程
学习笔记二之Java虚拟机中类加载的过程 当程序要使用某个类时,如果该类还未被加载到内存中,则系统会通过加载,连接,初始化三步来实现这个类进行初始化. 1. 加载 加载,是指Java虚拟机查找字 ...
- 程序员50题(JS版本)(三)
程序11:判断101~200之间有多少个素数,并输出所有素数 for(var i=101,num=0;i<=200;i++){ for(var j=2;j<=i;j++){ if(i%j= ...
- 简易仿ios菊花加载loading图
原文链接:https://mp.weixin.qq.com/s/wBbQgOfr59wntNK9ZJ5iRw 项目中经常会用到加载数据的loading显示图,除了设计根据app自身设计的动画loadi ...