07-OC特有語法02

分類-Category

1. 基本用途
  • 如何在不改變原來類模型的前提下,給類擴充一些方法?有2種方式
    • 繼承
    • 分類(Category)-- 可以給某一個類擴充一些方法(不修改原來類的代碼)
2. 格式
  • 分類的聲明
@interface 類名 (分類名稱)
// 方法聲明
@end
  • 分類的實現
@implementation 類名 (分類名稱)
// 方法實現
@end
3. 好處
  • 一個龐大的類可以分模塊開發
  • 一個龐大的類可以由多個人來編寫,更有利于團隊合作
4. 給系統自帶的類添加分類
  • 給NSString增加一個類方法:計算某個字符串中阿拉伯數字的個數
  • 給NSString增加一個對象方法:計算當前字符串中阿拉伯數字的個數
5. 注意
  • Category可以訪問原始類的實例變量,但不能添加變量,只能添加方法。如果想添加變量,可以考慮通過繼承創建子類
  • Category可以實現原始類的方法,但不推薦這么做,因為它是直接替換掉原來的方法,這么做的后果是再也不能訪問原來的方法
  • 多個Category中如果實現了相同的方法,只有最后一個參與編譯的才會有效

類的本質

1. 類也是個對象
  • 其實類也是一個對象,是Class類型的對象,簡稱“類對象”
  • Class類型的定義typedef struct objc_class *Class;
  • 類名就代表著類對象,每個類只有一個類對象
2. +load和+initialize
  • +load

    • 在程序啟動的時候會加載所有的類和分類,并調用所有類和分類的+load方法
    • 先加載父類,再加載子類;也就是先調用父類的+load,再調用子類的+load
    • 先加載元原始類,再加載分類
    • 不管程序運行過程有沒有用到這個類,都會調用+load加載
  • +initialize

    • 在第一次使用某個類時(比如創建對象等),就會調用一次+initialize方法
    • 一個類只會調用一次+initialize方法,先調用父類的,再調用子類的
3. 獲取類對象的2種方式

Class c = [Person class]; // 類方法
或者
Person *p = [Person new];
Class c2 = [p class]; // 對象方法

4. 類對象調用類方法

Class c = [Person class];
Person *p2 = [c new];

description方法

1. -description方法

使用NSLog和%@輸出某個對象時,會調用對象的-description方法,并拿到返回值進行輸出

2. + description方法

使用NSLog和%@輸出某個類對象時,會調用類對象+description方法,并拿到返回值進行輸出

3. 修改NSLog的默認輸出
  • 重寫-description或者+description方法即可
4. 死循環陷阱
  • 如果在-description方法中使用NSLog打印self

SEL

1. 方法的存儲位置
  • 每個類的方法列表都存儲在類對象中
  • 每個方法都有一個與之對應的SEL類型的對象
  • 根據一個SEL對象就可以找到方法的地址,進而調用方法
  • SEL類型的定義 typedef struct objc_selector *SEL;
2. SEL對象的創建
SEL s = @selector(test);
SEL s2 = NSSelectorFromString(@"test");
3. SEL對象的其他用法
// 將SEL對象轉為NSString對象
NSString *str = NSStringFromSelector(@selector(test));

Person *p = [Person new];
// 調用對象p的test方法
[p performSelector:@selector(test)];

NSLog輸出增強

  1. __ FILE __ :源代碼文件名
  2. __ LINE __ :NSLog代碼在第幾行
  3. _cmd :代表著當前方法的SEL
// 下面的代碼會引發死循環

- (void)test 
{
    [self performSelector:_cmd];  
}
最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。