Copy与mutableCopy的个人理解

1. 相同点

  • 都是将原有对象进行深拷贝(狭义)

    这里的狭义上的深拷贝指的是在不考虑编译器在编译时对不可变对象进行copy时采取的优化策略:即将不可变对象的地址直接赋值给拷贝对象,因为不可变对象无法进行修改,也就不存在拷贝后原值改变的情况,所以为了效率,即不再重新开辟空间,编译器对不可变对象采取了浅拷贝的方式。

    浅拷贝 :只是对指针的拷贝,拷贝后两个指针指向同一个内存空间。

    深拷贝 :不但对指针进行拷贝,而且对指针指向的内容进行拷贝,经深拷贝后的指针是指向两个不同地址的指针。

  • 都是为了防止因原对象改变而造成拷贝对象改变的策略

    不可变对象除外。

2.不同点

  • 无论是可变对象还是不可变对象进行copy,返回值一律是不可变对象(与被拷贝对象无关)

    可变对象copy后自然会拷贝一个新的地址给不可变类型的拷贝对象(深拷贝),而不可变对象因为优化策略则为浅拷贝

    NSMutableString* mstr=[NSMutableString stringWithString:@"1"];
    NSString *str=[mstr copy]; //将对象copy给不可变对象
    [mstr appendFormat:@"2"];//因为深拷贝,str不会因mstr改变而改变
    NSLog(@"%@",str); //输出1
    NSString* str0=@"1";
    NSMutableString *str1=[str0 copy];
    NSLog(@"%p:%p",str0,str1); //0x100001040:0x100001040 浅拷贝

    tips:当拷贝对象为可变对象时,使用copy会导致crash(在copy后使用append方法试图改变拷贝对象时)

    NSMutableString* mstr0=[NSMutableString stringWithString:@"1"];
    NSMutableString *mstr1=[mstr0 copy]; //将对象copy给可变对象
    [mstr0 appendFormat:@"2"];//因为深拷贝,mstr1不会因mstr0改变而改变
    NSLog(@"%@",str); //输出1
    [mstr1 appendFormat:@"2"];//crash,因为经过copy后mstr1已经变为了不可变对象(多态,NSMutableString是NSString的子类)
  • 无论是可变对象还是不可变对象进行mutableCopy,返回值一律是可变对象(与被拷贝对象无关,且狭义上深拷贝)

    狭义上的深拷贝指的是对于非容器类,而非容器类只是深拷贝容器,而容器内的对象则为指针拷贝(浅拷贝)

    容器类:NSArray、NSDictionary、NSSet

    如果要对容器类进行完全深拷贝,一般使用对象方法:-(id)initWithArray: copyItems:

    tips:当拷贝对象为不可变对象时,使用mutableCopy会将不可变对象改为可变对象

    NSString* str0=@"1";
    NSString *str1=[str0 mutableCopy]; //将对象mutableCopy给不可变对象
    [(NSMutableString *)str1 appendFormat:@"2"];//这里的str已经为可变对象,但编译器因为看不到可变对象的appendFormat方法,所以这里需要强转换为NSMutableString(若str这里不是真正指向可变对象,则会报错,但这里未报错,所以str已经指向了一个可变对象,即深拷贝)
    NSLog(@"%@",str1); //输出12

3.总结

无论是copy还是mutableCopy都可以看作是为了让被拷贝对象与拷贝对象进行分离,互不干扰的一种策略(通过深拷贝实现,虽然有两个例外:编译器优化(其实无影响)和容器类的假深拷贝)。只不过一个返回的是不可变对象,而另一个返回的是可变对象,仅此而已

Copy与mutableCopy的个人理解的更多相关文章

  1. 关于:1.指针与对象;2.深浅拷贝(复制);3.可变与不可变对象;4.copy与mutableCopy的一些理解

    最近对深浅拷贝(复制)做了一些研究,在此将自己的理解写下来,希望对大家有所帮助.本人尚处在摸索阶段,希望各位予以指正. 本文包括如下方向的探索: 1.指针与对象: 2.深/浅拷贝(复制): 3.可变/ ...

  2. iOS copy和mutableCopy 整理

    copy 和 mutableCopy 你真的理解吗?最近发现很多面试者基本都不能很好地回答这个问题.所以整理一下. copy和mutableCopy的概念: copy 浅拷贝,不拷贝对象本身,仅仅是拷 ...

  3. 对copy、mutableCopy理解

    Objective - C 中有很多在日常项目中经常用到的常用代码,在这里着重的讲一下关于copy 和 mutableCopy 的区别以及相关用法. Objective - C 中可变对象和不可对象经 ...

  4. 探讨NSString和NSMutableString的内存问题以及copy和MutableCopy两个方法

    NSString: //main.m #import <Foundation/Foundation.h> int main(int argc, const char * argv[]) { ...

  5. NSArray和NSMutableArray的copy和MutableCopy

    NSArray: //main.m #import <Foundation/Foundation.h> int main(int argc, const char * argv[]) { ...

  6. copy和mutableCopy都是浅拷贝!!!------你被骗了很多年

    所有系统容器类的copy或mutableCopy方法,都是浅拷贝!!! (ps:什么是容器?比如NSArray,NSMutableArray,NSDictionary,NSMutableDiction ...

  7. iOS copy 和 mutableCopy 学习

    (参考 iOS 52个技巧学习心得笔记 第二章 对象 , 消息, 运行期)的对象部分 关于Copy  有个经典问题”大部分的时候NSString的属性都是copy,那copy与strong的情况下到底 ...

  8. Objective-C中的Strong、Copy与MutableCopy

    面试过程中经常被问到ARC中Strong.Copy的区别是什么.普通的回答是:一样.文艺(正确)的回答是:分情况(我擦!WQY#$&Y**%OWEUR) 可以先参考这篇文章http://www ...

  9. 集合使用copy与mutableCopy的区别

    集合(NSArray,NSSet,NSDictionary等)使用copy与mutableCopy的区别是类似的,下面以NSMutableArray.NSArray 为例子验证如下: NSMutabl ...

随机推荐

  1. ES6新增的Map和WeakMap 又是什么玩意?非常详细的解释

    上一篇文章讲了set和weakSet,这节咱就讲Map和weakMap是什么?这两篇文章并没有什么联系,主要知识用法类似而已.嘿嘿,是不是感觉舒服多了. 什么是Map 介绍什么是Map,就不得不说起O ...

  2. php 可变变量 $$name

    //可变变量 $name = 'abc'; $$name = '; echo $name . "<br/>"; // abc echo $$name . echo $a ...

  3. 通过纯css实现图片居中的多种实现方式

    html结构: <div class="demo" style="width: 800px;height: 600px; border:1px solid #ddd ...

  4. dhcp协议抓包分析

    dhcp协议 DHCP,动态主机配置协议,前身是BOOTP协议,是一个局域网的网络协议,使用UDP协议工作,常用的2个端口:67(DHCP server),68(DHCP client). wires ...

  5. opencv-5-图像遍历与图像改变

    opencv-5-图像遍历与图像改变 opencvc++qt 目录 目录 开始 图像的像素点访问与遍历 opencv 座标定义 下标访问 指针访问 迭代器法访问 遍历访问时间对比 图像操作 图像叠加 ...

  6. asList和ArrayList不得不说的故事

    目录 简介 创建ArrayList UnsupportedOperationException asList 转换 总结 asList和ArrayList不得不说的故事 简介 提到集合类,ArrayL ...

  7. java 中的fork join框架

    文章目录 ForkJoinPool ForkJoinWorkerThread ForkJoinTask 在ForkJoinPool中提交Task java 中的fork join框架 fork joi ...

  8. Netty随记之ChannelInboundHandlerAdapter、SimpleChannelInboundHandler

    ChannelInboundHandlerAdapter ChannelInboundHandlerAdapter是ChannelInboundHandler的一个简单实现,默认情况下不会做任何处理, ...

  9. mybatis源码学习(四):动态SQL的解析

    之前的一片文章中我们已经了解了MappedStatement中有一个SqlSource字段,而SqlSource又有一个getBoundSql方法来获得BoundSql对象.而BoundSql中的sq ...

  10. Hyperf基础教程

    前提说明 本教程适用于新手.老手,也适用于任何操作系统,包括Windows.linux.MacOS 介绍 Hyperf 是基于 Swoole 4.4+ 实现的高性能.高灵活性的 PHP 协程框架,内置 ...