0x01 encode編譯器指令
@encode是編譯器指令之一。
@encode返回一個給定的Objective-C 類型編碼(Objective-C Type Encodings)。
這是一種內部表示的字符串,類似於 ANSI C 的 typeof 操作。
蘋果的 Objective-C 運行時庫(runtime)內部利用類型編碼幫助加快消息分發。
0x02 Objective-C類型編碼
0x03 Objective-C方法編碼
0x04 打印類型編碼舉例
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSLog(@"int : %s", @encode(int));
NSLog(@"float : %s", @encode(float));
NSLog(@"float * : %s", @encode(float*));
NSLog(@"char : %s", @encode(char));
NSLog(@"char * : %s", @encode(char *));
NSLog(@"BOOL : %s", @encode(BOOL));
NSLog(@"void : %s", @encode(void));
NSLog(@"void * : %s", @encode(void *));
NSLog(@"NSObject * : %s", @encode(NSObject *));
NSLog(@"NSObject : %s", @encode(NSObject));
NSLog(@"[NSObject] : %s", @encode(typeof([NSObject class])));
NSLog(@"NSError ** : %s", @encode(typeof(NSError **)));
int intArray[5] = {1, 2, 3, 4, 5};
NSLog(@"int[] : %s", @encode(typeof(intArray)));
float floatArray[3] = {0.1f, 0.2f, 0.3f};
NSLog(@"float[] : %s", @encode(typeof(floatArray)));
typedef struct _struct {
short a;
long long b;
unsigned long long c;
} Struct;
NSLog(@"struct : %s", @encode(typeof(Struct)));
return 0;
}
}
/*
Output:
2018-07-27 03:34:54.610 test[3084:97707] int : i
2018-07-27 03:34:54.611 test[3084:97707] float : f
2018-07-27 03:34:54.611 test[3084:97707] float * : ^f
2018-07-27 03:34:54.611 test[3084:97707] char : c
2018-07-27 03:34:54.611 test[3084:97707] char * : *
2018-07-27 03:34:54.611 test[3084:97707] BOOL : c
2018-07-27 03:34:54.612 test[3084:97707] void : v
2018-07-27 03:34:54.612 test[3084:97707] void * : ^v
2018-07-27 03:34:54.612 test[3084:97707] NSObject * : @
2018-07-27 03:34:54.612 test[3084:97707] NSObject : {NSObject=#}
2018-07-27 03:34:54.612 test[3084:97707] [NSObject] : #
2018-07-27 03:34:54.612 test[3084:97707] NSError ** : ^@
2018-07-27 03:34:54.612 test[3084:97707] int[] : [5i]
2018-07-27 03:34:54.612 test[3084:97707] float[] : [3f]
2018-07-27 03:34:54.612 test[3084:97707] struct : {_struct=sqQ}
Program ended with exit code: 0
*/
0x05 類型代碼的實用方法
遍歷NSArray或NSDictionary的時候,我們可能需要判斷當前位置的數據類型,再決定對應的操作方法:
NSDictionary *dic = [NSDictionary dictionaryWithObjectsAndKeys:
[NSNumber numberWithBool:YES],@"key1",
[NSNumber numberWithDouble:1.00f],@"key2",
[NSNumber numberWithInt:1],@"key3",
[NSNumber numberWithFloat:33.0f], @"key4",
nil];
//快速枚舉,僅適用於Objective-C 2.0
for(NSString *key in dic){
id value = [dic valueForKey:key];
if([value isKindOfClass:[NSNumber class]]){
const char * pObjCType = [((NSNumber*)value) objCType];
if (strcmp(pObjCType, @encode(int)) == 0) {
NSLog(@"字典中key=%@的值是int類型,值爲%d",key,[value intValue]);
}
if (strcmp(pObjCType, @encode(float)) == 0) {
NSLog(@"字典中key=%@的值是float類型,值爲%f",key,[value floatValue]);
}
if (strcmp(pObjCType, @encode(double)) == 0) {
NSLog(@"字典中key=%@的值是double類型,值爲%f",key,[value doubleValue]);
}
if (strcmp(pObjCType, @encode(BOOL)) == 0) {
NSLog(@"字典中key=%@的值是bool類型,值爲%i",key,[value boolValue]);
}
}
}