23

当我使用 Xcode 4.4 创建一个新项目并添加这些行时:

NSDictionary *test = @{ @"key" : @"test value" };
NSString *value = test[@"key"];
NSLog(@"value is: %@", value);

它编译时没有警告并按预期执行。

将相同的行添加到现有项目会产生编译器错误:

NSString *value = test[@"key"]; <-- Expected method to read dictionary element not found on object of type 'NSDictionary *'

我比较了这两个项目的目标构建设置,但没有任何结果。

更新: 成功编译的新项目是针对 OSX 的。我用上述几行尝试了另一个用于 iOS 的新版本,但它无法编译,与我先前存在的 (iOS) 项目相同。

4

1 回答 1

48

这与旧项目与新项目无关,而是您使用的 SDK 的一个因素。您遇到的问题是,虽然这是一个编译器功能,但它需要 SDK 支持。iOS 5 SDK 不提供这种支持,但 iOS 6 SDK 提供。

因此,现在您应该只使用 iOS 6 SDK。如果您想在 iOS 5 SDK 中使用对象下标,请继续阅读。

您需要做的就是添加一个头文件,以便编译器尝试调用。无需添加实现;它由 自动处理arclite。(如果您不使用 ARC,则必须强制链接器包含arclite. 但您仍然不必实际切换到它。)

创建一个新的接口文件NSObject+subscripts.h

#if __IPHONE_OS_VERSION_MAX_ALLOWED < 60000
@interface NSDictionary(subscripts)
- (id)objectForKeyedSubscript:(id)key;
@end

@interface NSMutableDictionary(subscripts)
- (void)setObject:(id)obj forKeyedSubscript:(id <NSCopying>)key;
@end

@interface NSArray(subscripts)
- (id)objectAtIndexedSubscript:(NSUInteger)idx;
@end

@interface NSMutableArray(subscripts)
- (void)setObject:(id)obj atIndexedSubscript:(NSUInteger)idx;
@end
#endif

我已经把这个块放在了github 上

NSObject注意:在解释如何将它们仅添加到相关对象之前,我曾经建议添加所需的方法。回想起来,我认为这是我的错误。它导致在运行时而不是编译时捕获错误,这与这里现在介绍的方法不同。这种方法仍然在我的博客上,但我现在认为它更像是一种很酷的 hack,而不是一种有用的方法。

来源:

于 2012-07-25T22:52:00.360 回答