采用递归的方法访问一个对象,讲其内容写到一个字典中
支持的成员变量类型:
1,NSString *
2,NSArray *
3,由1,2,构成的自定义类
+ (NSMutableDictionary *) getDicFromObject: (id) theObject
{
if ([theObjectisKindOfClass:[NSStringclass]])
{
return theObject;
}
NSMutableDictionary * tmpDic = [[[NSMutableDictionaryalloc] init] autorelease];
if (theObject ==nil)
{
return tmpDic;
}
//get all the property fields names
NSString *className =NSStringFromClass([theObject class]);
const char *cClassName = [className UTF8String];
id theClass = objc_getClass(cClassName);
unsignedint outCount, i;
objc_property_t *properties = class_copyPropertyList(theClass, &outCount);
NSMutableArray *propertyNames = [[NSMutableArrayalloc] initWithCapacity:1];
for (i = 0; i < outCount; i++)
{
objc_property_t property = properties[i];
NSString *propertyNameString = [[NSStringalloc] initWithCString:property_getName(property)
encoding:NSUTF8StringEncoding];
[propertyNamesaddObject:propertyNameString];
[propertyNameStringrelease];
NSLog(@"%s %s\n",property_getName(property), property_getAttributes(property));
}
for (NSString *keyin propertyNames)
{
SEL selector = NSSelectorFromString(key);
id value = [theObject performSelector:selector];
if (value == nil)
{
value = [NSNullnull];
[tmpDicsetObject:value forKey:key];
continue;
}
//[finalDict setObject:value forKey:key];
if ([valueisKindOfClass:[NSStringclass]])
{
[tmpDicsetObject:value forKey:key];
}
elseif ([value isKindOfClass:[NSArrayclass]])
{
NSMutableArray * valueArray = [[[NSMutableArrayalloc] init]autorelease];
NSArray * aArray = (NSArray *)value;
for (int i =0; i < [aArray count]; i++)
{
[valueArrayaddObject:[NetRequestManagergetDicFromObject:[aArray objectAtIndex:i]]];
//[tmpDic setObject:[NetRequestManager getDicFromObject:[aArray objectAtIndex:i]]
// forKey:key];
}
[tmpDicsetObject:valueArray forKey:key];
}
else
{
[tmpDicsetObject:[NetRequestManagergetDicFromObject:value] forKey:key];
}
}
return tmpDic;
}
调用示例
ContactBaseInfoObj * obj = [[ContactBaseInfoObjalloc] init];
obj.name = [[[NameObjalloc] init]autorelease];
obj.name.firstName =@"Jam";
obj.name.middleName =@"Alen";
obj.name.lastName =@"Green";
obj.primaryEmail =@"America";
NSMutableDictionary * tmpDic = [NetRequestManagergetDicFromObject:obj];
NSString * tmpStr = [tmpDicJSONRepresentation];
NSLog(tmpStr);
NSArray * ids = [NSArrayarrayWithObjects:@"mm",@"Mary", @"yy",nil];
ContactBaseWithBothIDObj * tmpCC = [[ContactBaseWithBothIDObjalloc] init];
tmpCC.contactBaseInfo = obj;
tmpCC.contactID =@"123456";
tmpCC.contactListIDs = ids;
tmpDic = [NetRequestManagergetDicFromObject:tmpCC];
tmpStr = [tmpDicJSONRepresentation];
NSLog(tmpStr);
NSString * testStr = [NetRequestManager getCodeFromObject:obj];
testStr = [NetRequestManager getCodeFromObject:tmpCC];
执行结果
{"primaryEmail":"America","primaryMobile":null,"name":null}
{"primaryEmail":"America","primaryMobile":null,"name":{"firstName":"Jam","middleName":"Alen","lastName":"Green"}}
{"contactID":"123456","contactBaseInfo":{"primaryEmail":"America","primaryMobile":null,"name":{"firstName":"Jam","middleName":"Alen","lastName":"Green"}},"contactListIDs":["mm","Mary","yy"]}
NSLog(@"%s %s\n",property_getName(property), property_getAttributes(property));
可以看到类名,再次
id theClass = objc_getClass(cClassName);
unsignedint outCount, i;
objc_property_t *properties = class_copyPropertyList(theClass, &outCount);
NSMutableArray *propertyNames = [[NSMutableArrayalloc] initWithCapacity:1];
就可以得到类结构成员变量的所有属性,可以通过递归的方法来获取到
一个类的结构可以看成是一个树结构
上面的程序是对任意符合条件的给定类的动态处理方法
可以扩展成一个代码生成器code maker 来生成一段具体的代码来处理一个具体的类,生成的处理代码也就是常规的对一个类的处理方式
这个扩展还是有些难度的,尽管在理论上是可行的