GeekBand:Oc第二周學(xué)習(xí)筆記

認(rèn)識(shí)oc字符串NSString

NSString是一個(gè)Unicode編碼簇爆、16位字符的字符序列
NSString被定義為類穷娱,引用類型,拷貝時(shí)具有引用語義
初始化方法:字面量初始化、初始化器砂缩、工廠方法
NSString擁有恒定性,所有的操作無法更改字符串本身三娩,如有更改都是返回新值的形式
NSString擁有共享機(jī)制庵芭,引用計(jì)數(shù)管理對其有特殊的管理規(guī)則
<small>恒定性與共享機(jī)制相輔相成,正因?yàn)橛辛斯蚕頇C(jī)制雀监,才需要恒定性來保證原字符串不發(fā)生變化双吆。同時(shí)共享機(jī)制也為系統(tǒng)內(nèi)存管理帶來了很大的好處,通常應(yīng)用中字符串的用量很大会前,如果每個(gè)相同的字符串都有一個(gè)自己的內(nèi)存空間好乐,那就會(huì)造成很大的資源浪費(fèi)。所以瓦宜,在oc中蔚万,當(dāng)我們申明一個(gè)字符串,而這個(gè)字符串在內(nèi)存中已經(jīng)存在临庇,那么該指針就會(huì)指向已存在的字符串地址上</small>

NSMutableString

NSMutableString具有可變性反璃,NSString具有恒定性
NSMutableString為NSString的子類
NSMutableString不具有共享性,NSString具有共享性
NSMutableString并不是在原有內(nèi)存上直接增長假夺,而是重新分配一個(gè)更大或更小的緩存容量存放字符

數(shù)組 列表 字典

<small>- 類型差不多淮蜈,這里主要詳細(xì)講數(shù)組</small>

認(rèn)識(shí)數(shù)組:

  • 數(shù)組是一個(gè)有序的元素序列,支持隨機(jī)存取已卷。索引從0開始梧田,索引訪問越界會(huì)拋出運(yùn)行時(shí)異常。注意與C語言不通。
  • NSArray被定義為class柿扣,引用類型肖方,拷貝時(shí)具有引用語義。
  • NSArray的元素必須是對象未状,即NSObeject的子類:
    1.如為基本數(shù)值類型俯画,須用NSNumber封裝為對象類型后,才能放入數(shù)組中司草。
    2.如為C語言結(jié)構(gòu)類型艰垂,須用NSValue封裝為對象類型后,才能放入數(shù)組中埋虹。
    3.數(shù)組元素可以是不用對象類型猜憎,可能會(huì)有類型不安全。
    注:對于類型不安全問題搔课,我們可以使用泛型來限制數(shù)組類型胰柑。ClassName<T>
    4.NSArra具有常量性:長度和元素指針都不能更改。但指針指向的對象內(nèi)部可以更改爬泥。

常用操作:

  • 數(shù)組遍歷:
    1.最快——Fast Enumeration 柬讨,直接訪問內(nèi)存,優(yōu)化索引檢查袍啡,快5-10倍踩官,用到了多線程。
        //快速枚舉
    for ( BLNPoint* point in array5)
    {
        point.x++;
        point.y++;
    }
    
    2.較慢——NSEnumerator遍歷:索引檢查+動(dòng)態(tài)消息調(diào)用
        //迭代器模式
    NSEnumerator *enumerator = [array5 objectEnumerator];
    BLNPoint* item;
    while (item = [enumerator nextObject])
    {
        item.x++;
        item.y++;
    }
    
    3.最慢——For循環(huán)訪問:索引檢查+動(dòng)態(tài)消息調(diào)用
        //for循環(huán)
    for (int i=0; i<array5.count; i++) {
        NSLog(@"array5[%d],%@",i,array5[i]);
    }
    
  • 注:for...in...利用了快速枚舉NSFastEnumerate
    當(dāng)我們想要改變數(shù)組變量中的數(shù)據(jù)或者刪除數(shù)組中的數(shù)據(jù)的時(shí)候,不能用for...in...境输。Objective-C中的foreach循環(huán)與Java中的相似蔗牡,在內(nèi)部是用iterator(迭代器)實(shí)現(xiàn)遍歷的。而不管是在Java還是C++中嗅剖,一旦修改了被遍歷對象辩越,在修改前生成的iterator都會(huì)失效,所以在用iterator遍歷集合時(shí)增刪集合元素
    NSArray的枚舉操作中有一條需要注意:對于可變數(shù)組進(jìn)行枚舉操作時(shí)信粮,你不能通過添加或刪除對象這類操作來改變數(shù)組容器黔攒。如果你這么做了,枚舉器會(huì)很困惑蒋院,而你將得到未定義的結(jié)果。
  • 解決方法:當(dāng)我們需要改變數(shù)組中的內(nèi)容時(shí)(這里指NSMutableArray可變數(shù)組),可以使用enumerateObjectsUsingBlock莲绰。
    [arr enumerateObjectsUsingBlock:^(NSMutableDictionary *obj, NSUInteger idx, BOOL *stop) { 
     if (...) {
          // do sth 
         *stop = YES; // 相當(dāng)于break ; stop控制跳出枚舉器.   
         }
    }];
    

//使用enumerateObjectsUsingBlock快速迭代欺旧,比起forloop要快。但是要再block中如果需要改變外部變量蛤签,那么需要在外部變量前聲明__block
```

可變數(shù)組(NSMutableArray)

1.NSMutableArray支持更改數(shù)組長度和元素指針辞友。為NSArray子類。
2.NSMutableArray初始化后,會(huì)分配一個(gè)緩存容量capacity称龙,一般大于實(shí)際元素?cái)?shù)量留拾,當(dāng)長度增長時(shí),如實(shí)際需求大于capacity鲫尊,其capacity會(huì)以近似二倍的方式指數(shù)增長痴柔。伴隨代價(jià):(1)分配新的堆內(nèi)存2*capacity (2)將原來堆內(nèi)存上的元素拷貝到新內(nèi)存(3)釋放原來的堆內(nèi)存
3.最佳實(shí)踐:估計(jì)好capacity,預(yù)先分配一定容量疫向,避免以后增長
4.盡量避免使用insertObject:atIndex:和removeObjectAtIndex:等操作咳蔚,因?yàn)闀?huì)改變數(shù)組元素序列,涉及大量內(nèi)存拷貝操作搔驼,代價(jià)高谈火。

ARC

自動(dòng)引用計(jì)數(shù)(Automatic Reference Counting)是OC默認(rèn)的內(nèi)存管理機(jī)制,針對堆上的對象舌涨,由編譯器自動(dòng)生成操作引用計(jì)數(shù)的指令(retain和release)糯耍,來管理對象的創(chuàng)建與釋放
新創(chuàng)建一個(gè)對象時(shí),它的引用計(jì)數(shù)為1囊嘉,retain操作計(jì)數(shù)+1温技,release-1;
當(dāng)一個(gè)對象的引用計(jì)數(shù)變?yōu)?的時(shí)候哗伯,內(nèi)存自動(dòng)釋放

自動(dòng)釋放池(Autorelease Pool)

release會(huì)導(dǎo)致對象立即釋放荒揣。如果頻繁對對象進(jìn)行release,可能會(huì)造成瑣碎的內(nèi)存管理負(fù)擔(dān)焊刹。autorelease可以將release的調(diào)用延遲到自動(dòng)釋放池被釋放時(shí)系任。
推薦使用自動(dòng)釋放池(Autorelease Pool)Block,當(dāng)其結(jié)束時(shí)虐块,所有接受autorelease消息的對象將會(huì)被立即釋放
大多數(shù)情況下俩滥,這樣使用就行了,無需程序員干預(yù)

何時(shí)需要手工管理Autorelease Pool贺奠?
1.編寫的程序不基于UI框架霜旧,如命令行程序

@autoreleasepool {
       block塊
       todo   

}

2.在循環(huán)中創(chuàng)建大量臨時(shí)對象,需要更早地釋放儡率,避免臨時(shí)對象聚集導(dǎo)致內(nèi)存峰值過大
3.在主線程之外創(chuàng)建新的線程挂据,在新線程開始執(zhí)行處,需要?jiǎng)?chuàng)建自己的Autorelease Pool儿普。
4.可以嵌套使用AutoreleasePool

認(rèn)識(shí)協(xié)議 Protocol

OC學(xué)習(xí)篇之---協(xié)議的概念和用法

協(xié)議:類型的合同約定崎逃,只描述外部申明,不提供具體實(shí)現(xiàn)眉孩。所以只有h文件
協(xié)議可以包含以下成員:
1.屬性
2.實(shí)例方法
3.類方法
4.初始化器——不常用
5.析構(gòu)器——不常用
協(xié)議中無法包含實(shí)例變量成員(實(shí)例變量是在m文件中)
協(xié)議中定義的屬性本質(zhì)上是訪問器方法个绍,編譯器不會(huì)合成實(shí)例變量

使用協(xié)議

@interface ClassName : NSObject<ProtocolName>
在聲明類文件時(shí) 勒葱,在類名后面用<ProtocolName>
一個(gè)類遵守協(xié)議,需要實(shí)現(xiàn)協(xié)議約定的所有@required成員
<small>協(xié)議中的屬性須在實(shí)現(xiàn)類的.h文件中申明(編譯器合成實(shí)例變量需要巴柿,而方法可以省略)</small>
注意編譯警告信息:
遵守協(xié)議后卻沒有實(shí)現(xiàn)必選協(xié)議方法時(shí)凛虽,會(huì)出現(xiàn)警告提示
協(xié)議類型變量被賦值非協(xié)議類型對象時(shí),會(huì)出現(xiàn)警告提示

協(xié)議本質(zhì)上是一種類型广恢,可以作為聲明類型凯旋,但不能創(chuàng)建實(shí)例

檢查協(xié)議類型
使用conformToProtocol:檢查對象是否實(shí)現(xiàn)了協(xié)議
if([obj conformToProtocol:@protocol(Aprotocol)])

OC中的協(xié)議就是相當(dāng)于Java中的接口(抽象類),只不過OC中的名字更形象點(diǎn)袁波,因?yàn)槲覀冊趯W(xué)習(xí)Java中的接口時(shí)候瓦阐,看可以知道其實(shí)接口就相當(dāng)于一種契約(協(xié)議),給他的實(shí)現(xiàn)類打上標(biāo)記了,當(dāng)然這個(gè)活在Java5.0之后篷牌,被注解替代了睡蟋,因?yàn)樽⒔饩褪菫榱舜斯δ苷Q生的。
協(xié)議就是定義了一組方法枷颊,然后讓其他類去實(shí)現(xiàn)
下面來看代碼:
WithProtocol.h

#import <Foundation/Foundation.h>  

@protocol WithProtocol <NSObject>

//默認(rèn)是必須實(shí)現(xiàn)的

//必須實(shí)現(xiàn)
@required

  • (void)finshTask;
  • (void)dontLate;

//可選實(shí)現(xiàn)
@optional

  • (void)wearNeat;

@end

>
>這里就定義了一個(gè)協(xié)議WithProtocl
協(xié)議的定義格式:

@protocol 協(xié)議名 <父協(xié)議>
定義方法
@end

- 注:定義協(xié)議的關(guān)鍵字是@protocol,同時(shí)協(xié)議也是可以繼承父協(xié)議的
>
協(xié)議中定義的方法還有兩個(gè)修飾符:
@required:這個(gè)表示這個(gè)方法是其他類必須實(shí)現(xiàn)的戳杀,也是默認(rèn)的值
@optional:這個(gè)表示這個(gè)方法對于其他類實(shí)現(xiàn)是可選的
這個(gè)就和類似與Java中的抽象類了,如果是abstract修飾的就必須實(shí)現(xiàn)夭苗,所以如果一個(gè)協(xié)議中沒有@optional修飾的方法信卡,那么這個(gè)協(xié)議就相當(dāng)于Java中的接口了。
>
- 這里要注意的是题造,上面的代碼中NSObject不是我們之前說的NSObject類了傍菇,而是NSObject協(xié)議,他也是OC中第一個(gè)協(xié)議界赔,這個(gè)名字相同在OC中是沒有關(guān)系的丢习。
再看一下協(xié)議的使用:

>```
>**Student.h**
>#import <Foundation/Foundation.h>  
>  
>#import "WithProtocol.h"  
>  
>@interface Student : NSObject <WithProtocol>  
>  
>- (void)study;  
>  
>@end
>```  
- 使用協(xié)議很簡單,直接在繼承類(NSObject)后面 <協(xié)議名>即可
>

>```
>#import "Student.h"  
  
>@implementation Student   
- (void)study{  
    NSLog(@"study");  
}  
//直接在.m文件中實(shí)現(xiàn)即可淮悼,不需要在.h文件中再次定義  
#pragma mark - WithProtocol  
//一般協(xié)議的方法咐低,在這里標(biāo)記下,用途是在導(dǎo)航欄快速地定位到這個(gè)方法是協(xié)議里的袜腥,起到分類的作用
- (void)finshTask{  
    NSLog(@"完成任務(wù)");  
}  
>- (void)dontLate{  
//#warning 代碼過幾天在補(bǔ)充  
    NSLog(@"不遲到");  
}    
>- (void)wearNeat{  
    NSLog(@"穿戴整潔");  
}    
>@end 

類別 Categroy

類別支持在沒有源代碼的情況下见擦,基于某些特定場合,為一個(gè)類增加功能
可以添加:1.類方法羹令;2.實(shí)例方法鲤屡;3.重寫基類方法
不能添加:1.屬性;2.實(shí)例變量福侈;3.已存在的同名方法
命名規(guī)范:類名+擴(kuò)展方法酒来,如:NSString+Drawing.h/.m

使用類別:

1.使用場景:

  • 適合在沒有源代碼的情況下,向已經(jīng)封裝的類中添加方法
  • 為一個(gè)類在某些特殊場景下增加功能
  • 對于復(fù)雜的大型文件分割實(shí)現(xiàn)

2.添加類別:

  • 自己創(chuàng)建的類
  • 系統(tǒng)的類
  • 第三方庫
BLNPoint.h
#import <Foundation/Foundation.h>
@interface BLNPoint : NSObject
{
   float _weight;
}

@property NSInteger x;
@property NSInteger y;
-(void)move;

@end

BLNPoint+Drawing.h
#import <Foundation/Foundation.h>
#import "BLNPoint.h"

@interface BLNPoint(Drawing)
-(void)draw;
//@property NSInteger weight;
-(void)setWeight:(NSInteger)weight;
-(NSInteger)weight;
@end

擴(kuò)展Extension

擴(kuò)展支持在編譯時(shí)癌刽、有類的源代碼的情況下,向類添加功能显拜≡盾可以將擴(kuò)展看做匿名的類別
接口定義在.m文件中@implementation前聲明,實(shí)現(xiàn)代碼仍然在@implementation中實(shí)現(xiàn)
擴(kuò)展支持添加以下成員:

  • 添加屬性
  • 添加實(shí)例成員
  • 添加類方法
  • 添加實(shí)例方法
  • 改寫屬性的讀寫屬性
@interface ClassName()
{
 聲明定義
}
@end

@implementation ClassName
{
 具體實(shí)現(xiàn)
}
@end

使用擴(kuò)展:

  • 擴(kuò)展實(shí)現(xiàn)的成員都只能在.m實(shí)現(xiàn)文件內(nèi)部訪問档址,在類外不可以直接訪問
  • 擴(kuò)展的主要用途在于信息隱藏邻梆,隱藏一些外部無需訪問,而內(nèi)部實(shí)現(xiàn)又需要使用的屬性尼摹、方法:
    1.類的主接口主要用于“對類外公開”的接口
    2.類的擴(kuò)展接口用于“對類內(nèi)可見”的接口
    <small>比如在類的主接口.h文件中有個(gè)屬性聲明為只讀屬性剂娄,我們可以在擴(kuò)展中升級(jí)這個(gè)屬性為讀寫屬性阅懦,這樣在類內(nèi)實(shí)現(xiàn)可以使用讀寫屬性,而對外只能是只讀屬性</small>
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末惯吕,一起剝皮案震驚了整個(gè)濱河市混埠,隨后出現(xiàn)的幾起案子诗轻,更是在濱河造成了極大的恐慌,老刑警劉巖吏颖,帶你破解...
    沈念sama閱讀 217,542評論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件半醉,死亡現(xiàn)場離奇詭異劝术,居然都是意外死亡呆奕,警方通過查閱死者的電腦和手機(jī)梁钾,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,822評論 3 394
  • 文/潘曉璐 我一進(jìn)店門姆泻,熙熙樓的掌柜王于貴愁眉苦臉地迎上來冒嫡,“玉大人孝凌,你說我怎么就攤上這事【海” “怎么了辜窑?”我有些...
    開封第一講書人閱讀 163,912評論 0 354
  • 文/不壞的土叔 我叫張陵穆碎,是天一觀的道長。 經(jīng)常有香客問我方面,道長恭金,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 58,449評論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮斤寂,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘罗侯。我一直安慰自己溪猿,他們只是感情好纫塌,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,500評論 6 392
  • 文/花漫 我一把揭開白布护戳。 她就那樣靜靜地躺著垂睬,像睡著了一般驹饺。 火紅的嫁衣襯著肌膚如雪缴渊。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,370評論 1 302
  • 那天蝌借,我揣著相機(jī)與錄音菩佑,去河邊找鬼凝化。 笑死搓劫,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的勤揩。 我是一名探鬼主播秘蛔,決...
    沈念sama閱讀 40,193評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼深员,長吁一口氣:“原來是場噩夢啊……” “哼辨液!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起止吁,我...
    開封第一講書人閱讀 39,074評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎盼理,沒想到半個(gè)月后宏怔,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體臊诊,經(jīng)...
    沈念sama閱讀 45,505評論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡斜脂,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,722評論 3 335
  • 正文 我和宋清朗相戀三年帚戳,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片偏友。...
    茶點(diǎn)故事閱讀 39,841評論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡约谈,死狀恐怖犁钟,靈堂內(nèi)的尸體忽然破棺而出棱诱,到底是詐尸還是另有隱情迈勋,我是刑警寧澤,帶...
    沈念sama閱讀 35,569評論 5 345
  • 正文 年R本政府宣布靡菇,位于F島的核電站米愿,受9級(jí)特大地震影響厦凤,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜育苟,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,168評論 3 328
  • 文/蒙蒙 一较鼓、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦博烂、人聲如沸香椎。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,783評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽畜伐。三九已至,卻和暖如春躺率,著一層夾襖步出監(jiān)牢的瞬間玛界,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,918評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人吕朵。 一個(gè)月前我還...
    沈念sama閱讀 47,962評論 2 370
  • 正文 我出身青樓阻问,卻偏偏與公主長得像第队,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子尸执,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,781評論 2 354

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