美文网首页大神ios
属性问题整理-Version0.3

属性问题整理-Version0.3

作者: 石丘 | 来源:发表于2015-08-01 18:59 被阅读120次

    内容针对ARC版本而言 如有遗漏和错误 还望指正

    属性的使用场景


    一般而言
    delegate、UI控件用weak
    block、NSString用copy
    基本数据类型int\float\BOOL\枚举\结构体 id 用assign
    上述对象外用strong

    属性的介绍


    assign与weak

    assign与weak都是简单赋值,不更改索引计数。

    assign看起来跟weak一样,其实不能混用的,assign的变量在释放后并不设置为nil(和weak不同),当你再去引用时候就会发生错误。

    两个的差别在于,weak用于对象类型,就是指针类型,而assign用于简单的数据类型,如int BOOL 等。

    基本数据类型不属于对象,它的创建和使用都是在栈中,超出对应方法体即被清除,所以不需要使用垃圾处理机制,无需记录索引值,所以使用assgin。

    assign是指针赋值,不对引用计数操作,使用之后如果没有置为nil,可能就会产生野指针;而weak一旦不进行使用后,永远不会使用了,就不会产生野指针!
    对应__weak关键字,与assign 相对应.weak用在arc下,assign用在mrc情况下用,weakassign多了一个在内存被销毁的情况下自动nil,防止野指针出现.
    UI控件之所以可以用弱指针 是因为控制器有强指针指向self.view, self.view有强指针指向subviews数组 数组中有强指针指向控件,代理必须是weak 因为代理一般都指向控制器 会造成循环引用 造成内存泄露.

    strong

    对应__strong关键字,即该属性所声明的变量将成为对象的持有者.与retain相对应,使用了引用计数,retain+1,release -1;当引用 计数为0时,dealloc会被调用,内存被释放

    copy

    对应__strong关键字,建立一个索引计数为1的对象,然后释放旧的对象.用于非共享内存时,每个指针有自己的内存空间.与strong 的区别是声明变量是拷贝对象的持有者.
    用copy的属性set 方法不能直接赋值要用 _xx = [xx copy]

    atomic(默认)

    线程安全型,在多线程中只能有一个线程能对它进行访问,非ARC编译环境下,需要设置访问锁来保证对该变量进行正确的get/set,防止在写未完成的时候被另外一个线程读取,造成数据错误。

    nonatomic

    非原子性访问
    非线程安全型,多个线程可以同时对其进行访问,当两个不同的线程对其访问时,容易失控.
    总结:atomic和nonatomic用来决定编译器生成的getter和setter是否为原子操作。在多线程环境下,原子操作是必要的,否则有可能引起错误的结果。加了atomic,setter函数会变成下面这样:
    <code>
    if (property != newValue) {
    [property release];
    property = [newValue retain];
    }
    </code>

    readonly

    只有get方法,没有set方法.

    readwrite

    默认属性,有get/set方法.

    unsafe_unretauined

    对应关键字__unsafe_unretained,声明一个弱应用,但是不会自动nil化,也就是说,如果所指向的内存区域被释放了,这个指针就是一个野指针了.所以很少使用用在ARC编译环境下,与assign相似.用于iOS 5之前的系统

    __block

    在block内部访问并修改外部变量时 外部变量需要用__block修饰
    只是引用的话不需要

    属性的使用场景


    @interface ViewController : UIViewController
    {
    //成员变量
        NSArray *array1;
    }
    //属性变量
    @property (nonatomic,strong) NSArray *array2;
    @end
    
    -(void)viewDidLoad
    {
        [super viewDidLoad];
        array1 = [[NSArray alloc] initWithObjects:@"abcde", nil];
        array2 = [[NSArray alloc] initWithObjects:@"123abc", nil];
    {
    //        局部变量
        NSArray *array1 = [[NSArray alloc] initWithObjects:@"12345", nil];
    }
        NSLog(@"\narray1 : %@\n array2 : %@",array1,array2);
    }
    

    局部变量是根据其生存周期定义的,在源文件中的array1,其生命周期是在以“{ }”为界限的代码块中,虽然它的名称与成员变量相同,但不是同一个变量。成员变量是用于一个区域内的临时变量。

    成员变量,本例中的是实例成员变量,是作用于整个类对象内的。从生命周期来看,它比局部变量要长一些,但它默认是私有的,其他对象是无法访问到的。因此,一般自定义方法,作为一个接口让其他对象访问这个变量。因此,成员变量用于类内部,无需与外界接触的变量。
    封装
    如果成员变量是private,程序中的其它对象很难直接访问该成员变量。如果是属性,相对更容易用父类方法读写属性。

    性能
    成员变量地址可以根据实例的内存地址偏移寻址。而属性的读写都需要函数调用,相对更慢。

    非基础类型
    对于复杂的C++类型,往往设为成员变量更合适,也许这种类型不支持copy,或者完全复制很麻烦。

    多线程
    多线程环境下,为保证数据一致性,在需要同步执行的代码段更应该使用成员变量。如果对需要同步更新的数据用getter/setter 方法,数据更新效率低,会带来更多的获取锁请求失败。

    程序正确性
    成员变量可以做直观的内存管理。属性可以一层层继承,还可以复写。容易出错。

    二进制文件的体积
    默认用属性,会生成不必要的getter/setter 方法,程序体积会变大。
    根据成员变量的私有性,为了方便访问,所以就有了属性变量。属性变量的好处就是允许让其他对象访问到该变量。当然,你可以设置只读或者可写等,设置方法也可自定义。所以,属性变量是用于与其他对象交互的变量。

    后记:

    没写属性的变量的默认 都是strong 缺省关键字就是__strong

    在用到block时的__block和__weak
    __block不管是ARC还是MRC模式下都可以使用,可以修饰对象,还可以修饰基本数据类型修饰对象可以在block中被重新赋值。
    __weak只能在ARC模式下使用,也只能修饰对象,不能修饰基本数据类型被修饰过的也并不可以重新赋值,目前见到和block一起用的最多的就是防止循环引用.__weak typeof(self) share = self

    关键字__autoreleasing

    __autoreleasing 都是用来修饰变量的.
    __autoreleasing 如用来修饰一个函数的参数,这个参数会在函数返回的时候被自动释放.
    在MRC下,使用autorelease让某个对象延迟释放
    -(ClassA *)TestMethod{ ClassA *classA = [[ClassA alloc] init]; return [classA autorelease];}
    在ARC下,需要使用如下方式替代:
    -(ClassA *)TestMethod{ __autoreleasing ClassA *classA = [ClassA alloc] init]; return classA;}
    或:
    -(NSString *)TestMethod:(_autoreleasing ClassA *)classA{ classA = [[ClassA alloc] init]; return classA;}

    strong 和copy


    strong
    copy

    https://www.mgenware.com/blog/?p=2121
    http://blog.csdn.net/liushuo19920327/article/details/51465318
    http://www.cnblogs.com/csj007523/archive/2012/07/23/2605662.html
    http://www.cnblogs.com/langtianya/p/3722129.html

    相关文章

      网友评论

      本文标题:属性问题整理-Version0.3

      本文链接:https://www.haomeiwen.com/subject/wxkvqttx.html