iOS深拷貝與淺拷貝

大家好半夷,我是西瓜,現(xiàn)居廣州极颓。在今年想要回顧梳理一下OC的相關(guān)知識點盅藻。今天就先從基礎(chǔ)但不簡單的深拷貝與淺拷貝開始吧购桑。

我們從一道當初很出名的面試題開始我們今天的學習:

為什么NSString要用copy修飾而不是strong?

我們先看第一個問題氏淑,為什么NSString要用copy而不用strong勃蜘。但凡有iOS基礎(chǔ)的同學們都知道,NSString是一個對象夸政,而對象就是用strong元旬,保證強引用不被釋放榴徐。與strong屬于同一層級的修飾詞還有weak守问,assign,copy坑资。weak和assign可以輕松的理解耗帕,唯獨讓人困惑的就是copy的用法。

接下里我們先看一段代碼:

@interface Person : NSObject

@property (nonatomic, copy) NSArray *array_copy;
@property (nonatomic, strong) NSArray *array_strong;

@end
    Person *p1 = [[Person alloc] init];

    NSMutableArray *array = [NSMutableArray arrayWithObjects:@"1", nil];
    
    p1.array_copy = array;
    p1.array_strong = array;
    
    NSLog(@"addObject之前 array 地址%p 值%@", array, array);
    NSLog(@"addObject之前 array_strong 地址%p 值%@", p1.array_strong, p1.array_strong);
    NSLog(@"addObject之前 array_copy 地址%p 值%@", p1.array_copy, p1.array_copy);
    
    [array addObject:@"2"];
    
    NSLog(@"addObject之后 array 地址%p 值%@", array, array);
    NSLog(@"addObject之后 array_strong 地址%p 值%@", p1.array_strong, p1.array_strong);
    NSLog(@"addObject之后 array_copy 地址%p 值%@", p1.array_copy, p1.array_copy);

打印結(jié)果如下:

2017-02-27 20:48:31.750 test[49360:1849602] addObject之前 array 地址0x60800005cc20 值(
    1
)
2017-02-27 20:48:31.750 test[49360:1849602] addObject之前 array_strong 地址0x60800005cc20 值(
    1
)
2017-02-27 20:48:31.751 test[49360:1849602] addObject之前 array_copy 地址0x608000011d30 值(
    1
)
2017-02-27 20:48:31.751 test[49360:1849602] addObject之后 array 地址0x60800005cc20 值(
    1,
    2
)
2017-02-27 20:48:31.751 test[49360:1849602] addObject之后 array_strong 地址0x60800005cc20 值(
    1,
    2
)
2017-02-27 20:48:31.751 test[49360:1849602] addObject之后 array_copy 地址0x608000011d30 值(
    1
)

有基礎(chǔ)的同學看看這段代碼袱贮,然后仔細思考一番應(yīng)該就能想通為什么是這個打印結(jié)果了仿便。

不過沒事,下面我會來一一講解攒巍。
我們首先創(chuàng)建了一個可變數(shù)組叫array嗽仪,接著把array賦值給Person的兩個屬性,這兩個屬性都是不可變數(shù)組柒莉,唯一的區(qū)別就是一個用copy修飾闻坚,一個用strong修飾。

接著我們分別打印array兢孝,array_strong窿凤,array_copy的值和地址,發(fā)現(xiàn)三個數(shù)組的值都是一樣的跨蟹,但array_copy的地址卻和其他兩個數(shù)組不相同雳殊,這是為什么呢?

最后我們給array可變數(shù)組添加一個字符串窗轩,再次打印夯秃,發(fā)現(xiàn)arrayarray_copy無論是地址還是值都一樣,但array_strong卻獨樹一幟,無論是值還是地址仓洼,都和其它二位不相同箫措。

其中p1.array_copy = array由于array_copycopy修飾的,所以這段代碼會產(chǎn)生類似于p1.array_copy = [array copy]的效果衬潦。

出現(xiàn)這樣的原因就是因為發(fā)生了深拷貝和淺拷貝斤蔓。

通俗來說,指針有變化就是深拷貝镀岛,指針無變化就是淺拷貝

如果把Person中的數(shù)組變成NSString弦牡,結(jié)果也是類似的。這樣我們就可以回答第一個問題了:

NSString使用copy是為了防止被賦值后再被外界所修改

按道理講NSArray漂羊,NSDictionary這些容器對象也應(yīng)該使用copy驾锰,以防止出現(xiàn)上述例子中出現(xiàn)的問題,但這個說法早就已經(jīng)過時了走越。使用copy還是strong完全取決于你的需求椭豫。你希望跟隨外界改動就用strong,不希望就用copy旨指。

粗略的畫了這張圖來解釋上述例子赏酥,不要介意:

屏幕快照.png

所以我們可以得出簡單的結(jié)論

淺拷貝:一個指針,指向一塊內(nèi)存谆构, 對這塊內(nèi)存進行淺拷貝裸扶,其實就是提取了這塊內(nèi)存的地址,把他給另外一個指針類型存放搬素。

綜合來看呵晨,內(nèi)存并未有任何變化,但是現(xiàn)在有兩個指針指向它熬尺。并且這兩個指針存放的值一樣摸屠,就是這塊內(nèi)存的地址,但是這兩個指針本身的內(nèi)存地址不一樣粱哼,所以就是兩個不同的指針指向同一塊內(nèi)存季二。


深拷貝: 一個指針,指向一塊內(nèi)存1皂吮,對這塊內(nèi)存1進行深拷貝戒傻,首先,我要開辟一塊跟這塊內(nèi)存一樣大的內(nèi)存2蜂筹,然后把內(nèi)存1里面的值(請注意需纳,這里是值)的復制到內(nèi)存2里,然后再建一個指針艺挪,指向內(nèi)存2不翩。

這時候來看兵扬,存在兩塊內(nèi)存,并且兩塊內(nèi)存毫不相干口蝠,只是里面的值暫時一樣而已器钟。 修改其中一個也不會影響另一個。

第一次寫技術(shù)文章妙蔗,肯定有諸多不足傲霸,請多包容。如果有不懂的或者想要技術(shù)交流都可以私信我眉反,謝謝大家昙啄。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市寸五,隨后出現(xiàn)的幾起案子梳凛,更是在濱河造成了極大的恐慌,老刑警劉巖梳杏,帶你破解...
    沈念sama閱讀 221,635評論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件韧拒,死亡現(xiàn)場離奇詭異,居然都是意外死亡十性,警方通過查閱死者的電腦和手機叛溢,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,543評論 3 399
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來烁试,“玉大人雇初,你說我怎么就攤上這事〖跸欤” “怎么了?”我有些...
    開封第一講書人閱讀 168,083評論 0 360
  • 文/不壞的土叔 我叫張陵郭怪,是天一觀的道長支示。 經(jīng)常有香客問我,道長鄙才,這世上最難降的妖魔是什么颂鸿? 我笑而不...
    開封第一講書人閱讀 59,640評論 1 296
  • 正文 為了忘掉前任,我火速辦了婚禮攒庵,結(jié)果婚禮上嘴纺,老公的妹妹穿的比我還像新娘。我一直安慰自己浓冒,他們只是感情好栽渴,可當我...
    茶點故事閱讀 68,640評論 6 397
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著稳懒,像睡著了一般闲擦。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 52,262評論 1 308
  • 那天墅冷,我揣著相機與錄音纯路,去河邊找鬼。 笑死寞忿,一個胖子當著我的面吹牛驰唬,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播腔彰,決...
    沈念sama閱讀 40,833評論 3 421
  • 文/蒼蘭香墨 我猛地睜開眼定嗓,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了萍桌?” 一聲冷哼從身側(cè)響起宵溅,我...
    開封第一講書人閱讀 39,736評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎上炎,沒想到半個月后恃逻,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,280評論 1 319
  • 正文 獨居荒郊野嶺守林人離奇死亡藕施,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 38,369評論 3 340
  • 正文 我和宋清朗相戀三年寇损,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片裳食。...
    茶點故事閱讀 40,503評論 1 352
  • 序言:一個原本活蹦亂跳的男人離奇死亡矛市,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出诲祸,到底是詐尸還是另有隱情浊吏,我是刑警寧澤,帶...
    沈念sama閱讀 36,185評論 5 350
  • 正文 年R本政府宣布救氯,位于F島的核電站找田,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏着憨。R本人自食惡果不足惜墩衙,卻給世界環(huán)境...
    茶點故事閱讀 41,870評論 3 333
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望甲抖。 院中可真熱鬧漆改,春花似錦跃赚、人聲如沸返吻。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,340評論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽氛魁。三九已至暮顺,卻和暖如春厅篓,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背捶码。 一陣腳步聲響...
    開封第一講書人閱讀 33,460評論 1 272
  • 我被黑心中介騙來泰國打工羽氮, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人惫恼。 一個月前我還...
    沈念sama閱讀 48,909評論 3 376
  • 正文 我出身青樓档押,卻偏偏與公主長得像,于是被迫代替她去往敵國和親祈纯。 傳聞我的和親對象是個殘疾皇子令宿,可洞房花燭夜當晚...
    茶點故事閱讀 45,512評論 2 359

推薦閱讀更多精彩內(nèi)容

  • 1、對象拷貝有兩種方式:淺復制和深復制腕窥。顧名思義粒没,淺復制,并不拷貝對象本身簇爆,僅僅是拷貝指向?qū)ο蟮闹羔橊桑簧顝椭剖侵苯?..
    滴答大閱讀 775評論 0 2
  • 1.什么情況使用關(guān)鍵字copy? 相比 assign 有什么不同哨毁? (1).在 ARC 中枫甲,在有可能出現(xiàn)循環(huán)引用的...
    愛賺錢的依米閱讀 2,037評論 0 22
  • 淺拷貝:拷貝容易本身,返回一個對象,指向相同的內(nèi)存地址. 深層復制:拷貝容器本身,返回一個對象,指向不同的內(nèi)存地址...
    CoderShmily閱讀 7,016評論 5 9
  • 看完很多同學給我的留言想幻,我只想說一句:孟老師很憂傷,真的很憂傷迎捺。因為太多同學不知道該如何提問举畸。所以我決定今天在回答...
    孟享專欄閱讀 311評論 0 3
  • 今天的淚水,會是你明天的成長凳枝;今天的傷痕,會是你明天的堅強跋核!有些路岖瑰,只能一個人走,路上的艱辛砂代,只有自己知道蹋订。不悲過...
    Nadirou閱讀 123評論 0 0