Objective-C学习笔记-回调

1.OC中有四种方法实现回调,分别是目标-动作对,辅助对象,通知,Block对象

2.目标-动作对,是指当某个事件发生时,向指定对象发送指定消息,计时器使用的就是目标-动作对机制,如下代码所示,每隔两秒会执行一次updateLastTime方法,其中NSRunLoop用来保持线程允许并处理事件

- (void)updateLastTime:(NSTimer *)t{
    NSLog(@"timer is %@",t);
}

#import <Foundation/Foundation.h>
#import "MyDesktop.h"

int main(int argc, const char * argv[]) {
    @autoreleasepool {

        MyDesktop *desktop=[[MyDesktop alloc] init];
        __unused NSTimer *timer=[NSTimer scheduledTimerWithTimeInterval:2.0 target:desktop selector:@selector(updateLastTime:) userInfo:nil repeats:YES];
        [[NSRunLoop currentRunLoop] run];
    
    }
    return 0;
}

3.辅助对象,是指当某个事件发生时,根据协议(可以理解为Java里的Interface)向辅助对象发送消息,所以辅助对象必须实现要求的协议才能接受消息

//声明
@interface MyDesktop : NSObject<NSURLConnectionDelegate,NSURLConnectionDataDelegate>

@end

//实现
@implementation MyDesktop
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data{
    NSLog(@"recevive data size is %ld",[data length]);
}

- (void)connectionDidFinishLoading:(NSURLConnection *)connection{
    NSLog(@"Got it all");
}

- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error{
    NSLog(@"%@",[error localizedDescription]);
}

@end

int main(int argc, const char * argv[]) {
    @autoreleasepool {

        MyDesktop *desktop=[[MyDesktop alloc] init];
        NSURL *url=[NSURL URLWithString:@"http://www.baidu.com"];
        NSURLRequest *request=[NSURLRequest requestWithURL:url];
        __unused NSURLConnection *coon=[[NSURLConnection alloc] initWithRequest:request delegate:desktop startImmediately:YES];
        [[NSRunLoop currentRunLoop] run];
    
    }
    return 0;
}

4.通知,苹果公司提供了一种称为通知中心的对象,可以通过通知中心等待某个通知出现时,向指定的对象发送指定的消息,下面是监听系统时区改变的代码

@interface MyDesktop : NSObject
-(void)zoneChanged:(NSNotification *)note;
@end


@implementation MyDesktop
-(void)zoneChanged:(NSNotification *)note{
    NSLog(@"zone changed!");
}
@end


int main(int argc, const char * argv[]) {
    @autoreleasepool {

        MyDesktop *desktop=[[MyDesktop alloc] init];
        [[NSNotificationCenter defaultCenter] addObserver:desktop
                                                 selector:@selector(zoneChanged:)
                                                 name:NSSystemTimeZoneDidChangeNotification
                                                 object:nil];
        [[NSRunLoop currentRunLoop] run];
    
    }
    return 0;
}

5.Block对象有点像Java里的匿名函数,C里面的函数指针,使用时要注意以下两点

  • Block对象中使用外部变量是只读的,如果想修改外部变量,需要在外部变量前面加上__block修饰
  • Block对象使用外部变量时,会持有它们(强引用),所以要避免造成强引用循环
int main(int argc, const char * argv[]) {
    @autoreleasepool {

        MyDesktop *desktop=[[MyDesktop alloc] init];
        //弱引用
        __weak MyDesktop *weakDesktop=desktop;
        //赋值
        [desktop setHeight:222];
        
        void (^MyBlock)(NSString *,NSUInteger);
        MyBlock=^(NSString * str,NSUInteger value){
            //避免对象被释放
            MyDesktop *innerDesktop=weakDesktop;
            NSLog(str,innerDesktop.height+value);
        };
        
        MyBlock(@"test value is %ld",1111);
    
    }
    return 0;
}
posted @ 2018-09-24 20:29  土豆吞噬者  阅读(140)  评论(0编辑  收藏  举报