0

我一直在研究这个问题一段时间,似乎无法找到解决方案。在我的应用程序中,我根据创建日期唯一标识联系人ABAddressBook,因为不能同时创建两个联系人。在我的应用程序中,创建日期存储在一个名为 的字符串中uid,如下所示。我正在检查两个联系人是否相同,我通过执行以下条件语句来做到这一点:

NSString *uid = @"some string";

if([(__bridge_transfer NSString *)ABRecordCopyValue(currentPersonRef, kABPersonCreationDateProperty) isEqualToString:uid]) {

    //Do some code
}

但是,当我运行此代码时,出现以下错误:

[__NSDate isEqualToString:]:无法识别的选择器发送到实例 0x8c7c770

我很确定问题在于ABRecordCopyValue()返回的 NSDate 对象没有被转换为NSString(__bridge_transfer NSString *)所以当我将它与uidusing进行比较时isEqualToString,它会崩溃。问题是,我认为通过将其转换为 NSString 对象isEqualToString:会起作用。我的问题是:

为什么 (__bridge_transfer NSString *) 不强制转换 NSDate 对象?


编辑:

提供的答案很有用,但它们并没有完全解决我的问题(实际上他们确实如此,但我有一个后续问题)。在我的代码的另一部分,我运行这个:

NSString *uid = (__bridge_transfer NSString *)ABRecordCopyValue(currentPerson, kABPersonCreationDateProperty);

如果我 NSLoguid我得到这个:

2012-10-28 21:55:29 +0000

那么如果不起作用,我将如何uid在上述条件语句中进行比较?isEqualToString:

4

2 回答 2

5

强制转换永远不会改变对象的类或类型。它只是告诉编译器,你确信这个对象是另一种类型,而不是编译器可能假设的。

因此,如果您将日期对象转换为字符串,它仍然是日期对象。

在 OOP 中,您通常需要向上转换:一个方法希望您传入一个对象,但实际上您传入的是子类的一个对象。如果您随后需要访问由子类定义的属性或方法,您将通过强制转换告诉编译器您拥有子类的对象。
iOS 中一个非常常见的示例是tableview:cellForRowAtIndexPath:子类单元格。

在 cocoa(-touch) 中,您还知道免费桥接的铸造。请参阅此文档以获取有效的演员表。


提供的答案很有用,但它们并没有完全解决我的问题(实际上他们确实如此,但我有一个后续问题)。在我的代码的另一部分,我运行这个:

NSString *uid = (__bridge_transfer NSString *)ABRecordCopyValue(currentPerson, kABPersonCreationDateProperty);

如果我 NSLog uid 我得到这个:

2012-10-28 21:55:29 +0000

您正在创建一个变量,您将其声明为 NSString,但实际上您分配给它的对象是一个日期对象。

NSDate *uidDate = (__bridge_transfer NSDate *)ABRecordCopyValue(currentPerson, kABPersonCreationDateProperty);

NSString *uid = [NSString stringWithFormat:uidDate];
于 2012-10-29T02:40:35.640 回答
0

好吧,我不知道你的问题的答案,但你为什么不直接将 ABRecordCopyValue() 转换为 NSString,然后执行 isStringEqual:?

像 -

NSString *string = [NSString stringWithFormat:@"%@", ABRecordCopyValue(currentPersonRef, kABPersonCreationDateProperty)];
if([string isEqualToString: uid]){
    //do your thing
}
于 2012-10-29T02:35:05.493 回答