zoukankan      html  css  js  c++  java
  • Objective-C中.h文件、.m文件中@interface、@synthesize及其它

    很多开发iOS好几年的老鸟,可能都不太分的清.h文件和.m文件里各种结构的用途和区别。最近仔细研究了一下,写一篇文章记下来。 
    一般的,写一个Class的时候,经常是这种格式(以UIViewController为例):

    .h文件:

    @interface ClassName{
        NSString* _value1;
    }
    
    @property(nonatomic,assign)NSString* value1;
    
    -(void)func1;
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8

    .m文件:

    @interface ClassName(){
    }
    @end
    
    @synthesize value1;
    
    @implementation ClassName
    
    -(void)func1{
    }
    
    @end
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    大体上就是这个格式。很多人,包括我,在创建和使用Class时,直接就使用这样的模板。这个模板里有一些有意思的小东西,值得探讨,比如: 
    1. 为什么.h文件和.m文件里各有1个@interface?它们分别有什么用? 
    2. .h中,value1为什么要定义2遍? 
    3. @synthesize有什么用? 
    还有一些其它的问题,今天先解决上面提到的这几个。

    为什么.h文件和.m文件里各有1个@interface?它们分别有什么用?

    .h里面的@interface,不消说,是典型的头文件,它是供其它Class调用的。它的@property和functions,都能够被其它Class“看到”。

    而.m里面的@interface,在OC里叫作Class Extension,是.h文件中@interface的补充。但是.m文件里的@interface,对外是不开放的,只在.m文件里可见。

    因此,我们将对外开放的方法、变量放到.h文件中,而将不想要对外开放的变量放到.m文件中(.m文件的方法可以不声明,直接用)。

    有的同学看到Class Extension,可能会想到OC里的@protocol。是的,它们都是对一个Class的扩展。不过它们的区别也很明显:

    Class Extension只能用在能得到源代码的情况下,而@protocol在得不到源码的时候也可以使用。

    因此@protocol一般用作对一些系统Class的扩展,常见的比如对NSString、UIView等。

    .h中,value1为什么要定义2遍?

    当然,现在@interface{}里的定义也可以省略掉了,不过原理还是要搞清楚。

    严格来说@interface{}里定义的变量,叫作instance variable,它是这个Class内部真正的全局变量。然而这个instance variable是不对外公开的,因此我们还需要一个对外公开的东西来调用,就是@property 
    @property是对外的,它其实是告诉大家,我这个Class里,有一个变量的set/get方法。比如,@property NSString* string; 就是说,本Class里有一个getString/setString供你们调用。

    因此需要2次声明。当然现在lldb也升级了,只要你声明了@property,它就可以自动创建对应的全局变量。

    @synthesize有什么用?

    @property 一个变量后,在@implementation里再@synthesize一下,相信是很多人的习惯。但是为什么要有这个@synthesize方法呢?

    @property是对外声明了Class的get/set方法,然后我们就需要在.m文件里手写get/set方法。这可就麻烦了,1个变量对应2个方法,假如一个Class里有10个变量,那岂不是要写20个方法?烦也烦死唠。

    @synthesize帮我们解决了这个问题。@synthesize在.m文件里自动生成了get/set方法。因此,我们只要在@implementation后面加上一行:@synthesize 就可以自动生成get/set方法了,省掉了很多麻烦。比如@synthesize value1 = _value1;的意思就是,将instance variable _value1用作getValue1和setValue1方法里。

    get/set方法有时候是比较复杂的,因为它和变量的属性相关,就是@property(nonatomic, assign/retain(strong/weak))这就和内存有关了。然而@synthesize为我们做了这些事情,就不要再为这些事情烦恼了!

    更方便的是,从Xcode4.4开始,编译器会自动为每一条@property都添加一条对应的@synthesize,因此以后我们只要写一个@property就可以了!

    PS:这些在Swift貌似都不是个事儿了。话说到现在都没怎么接触过Swift,真是罪过罪过。

  • 相关阅读:
    erlang 大神
    Mysql5.7全新的root密码规则
    单机多实例
    mysql 5.7源码安装
    MySQL审计功能
    MySQL升5.6引发的问题
    一千行MySQL学习笔记
    MySQL5.6新特性之GTID、多线程复制
    正确修改MySQL最大连接数的三种好用方案
    MYSQL 慢日志
  • 原文地址:https://www.cnblogs.com/to-creat/p/5223138.html
Copyright © 2011-2022 走看看