KVO,即:Key-Value Observing,它提供一种机制,当指定的对象的属性被修改后,则对象就会接受到通知。简单的说就是每次指定的被观察的对象的属性被修改后,KVO就会自动通知相应的观察者了。
二,使用方法系统框架已经支持KVO,所以程序员在使用的时候非常简单。
1. 注册,指定被观察者的属性,
2. 实现回调方法
3. 移除观察
三,实例:假设一个场景,股票的价格显示在当前屏幕上,当股票价格更改的时候,实时显示更新其价格。
1.定义数据模型(为了使用KVC)
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
@interface StockData : NSObject{
NSString *stockName;
float price;
}
@end
NS_ASSUME_NONNULL_END
2.viewcontroller详细实现
#import "StockViewController.h"
#import "StockData.h"
@interface StockViewController ()
@property(nonatomic,strong) StockData *stockData;
@property (weak, nonatomic) IBOutlet UILabel *myLabel;
@end
@implementation StockViewController
- (void)viewDidLoad {
[super viewDidLoad];
self.stockData = [StockData new];
[self.stockData setValue:@"searph" forKeyPath:@"stockName"];
[self.stockData setValue:@"10.0" forKeyPath:@"price"];
//1.注册
[self.stockData addObserver:self forKeyPath:@"price" options:NSKeyValueObservingOptionNew|NSKeyValueObservingOptionOld context:NULL];
}
//2.实现回调
/**
(lldb) po keyPath
price
(lldb) po object
<StockData: 0x600003a9bee0>
(lldb) po change
{
kind = 1;
new = 20;
old = 10;
}
(lldb) po context
<nil>
(lldb) po [change valueForKey:@"new"]
20
(lldb) po [change valueForKey:@"old"]
10
(lldb)
*/
-(void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSKeyValueChangeKey,id> *)change context:(void *)context{
if (object == self.stockData && [keyPath isEqualToString:@"price"]) {
self.myLabel.text = [NSString stringWithFormat:@"%.2f",[[self.stockData valueForKey:@"price"] floatValue]];
}
}
static float price;
- (IBAction)btnAction:(id)sender {
price+=20.00;
[self.stockData setValue:[NSString stringWithFormat:@"%f",price] forKey:@"price"];
}
//3.移除观察者
-(void)dealloc{
[self.stockData removeObserver:self forKeyPath:@"price"];
}
/*
#pragma mark - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
// Get the new view controller using [segue destinationViewController].
// Pass the selected object to the new view controller.
}
*/
@end
四,小结
KVO这种编码方式使用起来很简单,很适用与datamodel修改后,引发的UIVIew的变化这种情况,就像上边的例子那样,当更改属性的值后,监听对象会立即得到通知。
源码地址:https://github.com/wvqusrtg/NIiOS