在我的iPhone应用程序中,我有一个名为Contact
的课程,其中包含ABRecordRef
作为特定联系人的参考。
我需要在NSUserDefaults
中存储这些联系人的群组,但由于Contact
是自定义类,因此事情进展不顺利。
关于在这种情况下该怎么做的任何想法?
答案 0 :(得分:29)
您不能将NSUserDefaults
用于自定义类。来自文档:
NSUserDefaults
类提供了便于访问的方法 常见类型,例如浮点数,双精度数,整数,布尔值和URL。一个 默认对象必须是属性列表,即(或 对于集合的实例组合:NSData
,NSString
,NSNumber
,NSDate
,NSArray
或NSDictionary
。如果你想存储任何 在其他类型的对象中,通常应将其存档以创建NSData
的实例。
尝试使用NSData
。例如,要将自定义对象加载到数组中,您可以执行
NSUserDefaults *currentDefaults = [NSUserDefaults standardUserDefaults];
NSData *dataRepresentingSavedArray = [currentDefaults objectForKey:@"savedArray"];
if (dataRepresentingSavedArray != nil)
{
NSArray *oldSavedArray = [NSKeyedUnarchiver unarchiveObjectWithData:dataRepresentingSavedArray];
if (oldSavedArray != nil)
objectArray = [[NSMutableArray alloc] initWithArray:oldSavedArray];
else
objectArray = [[NSMutableArray alloc] init];
}
要归档数据,请使用:
[[NSUserDefaults standardUserDefaults] setObject:[NSKeyedArchiver archivedDataWithRootObject:objectArray] forKey:@"savedArray"];
只要您的自定义对象符合NSCoding
协议:
- (void)encodeWithCoder:(NSCoder *)coder;
{
[coder encodeObject:label forKey:@"label"];
[coder encodeInteger:numberID forKey:@"numberID"];
}
- (id)initWithCoder:(NSCoder *)coder;
{
self = [[CustomObject alloc] init];
if (self != nil)
{
label = [coder decodeObjectForKey:@"label"];
numberID = [coder decodeIntegerForKey:@"numberID"];
}
return self;
}
ABRecord
是一种不透明的C类型,因此它不是Objective-C意义上的对象。这意味着您无法扩展它,您无法在其上添加类别,您无法发送消息。您唯一能做的就是调用ABRecord
参考中描述的函数,并将ABRecord
作为参数。
您可以做两件事来保持ABRecord
所引用的信息:
按ABRecord
获取id
s ABRecordGetRecordID()
。 ABRecordID
被定义为int32_t,因此您可以将其转换为NSInteger
并将其存储在您喜欢的任何位置。您可以稍后从ABAddressBookGetPersonWithRecordID()
或ABAddressBookGetGroupWithRecordID()
获取记录。但是,用户或其他应用程序可以更改甚至删除记录。
将记录中的所有值复制到标准NSObject
子类,并使用上面讨论的NSCoding
来存储它。当然,您将不会受益于用户可能对记录所做的更改或添加。
答案 1 :(得分:2)
嗯,Apple's recommendation是存储记录标识符,名字和姓氏。然后,您可以尝试通过标识符从地址簿中检索联系人,如果找不到记录或者不是合适的人,请尝试按名字和姓氏检索(因为记录标识符可能会根据您的来源而变化)地址簿数据)。
这可能是您想要的,也可能不是,这取决于您存储数据的原因。但是,您可以很容易地将这三个值放入NSDictionary中并将字典写入NSUserDefaults
。
答案 2 :(得分:1)
ABRecordRef似乎是const void *
,因此请将其存储在NSUserDefaults
中,您必须将其包含在NSData
:NSData *d = [[NSData alloc] initWithBytes:thePointer length:sizeof(ABRecordRef)];
中。
答案 3 :(得分:0)
您可以使用转换为vCard表示实际存储它,这是CFStringRef,可以很容易地用作NSString。