【发布时间】:2012-10-25 21:03:33
【问题描述】:
我在 Xcode 中尝试使用 TabBarController 模板进行一些操作时遇到了这个“问题”(这不是真正的问题,我只是对这可能发生感到惊讶)。如果您使用没有故事板的模板,则基本设置如下所示:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
UIViewController *viewController1 = [[FirstViewController alloc] initWithNibName:@"FirstViewController" bundle:nil];
UIViewController *viewController2 = [[SecondViewController alloc] initWithNibName:@"SecondViewController" bundle:nil];
self.tabBarController = [[UITabBarController alloc] init];
self.tabBarController.viewControllers = @[viewController1, viewController2];
self.window.rootViewController = self.tabBarController;
[self.window makeKeyAndVisible];
return YES;
}
tabBarController 的 viewControllers 属性是一个 NSArray。因此[self.tabBarController objectAtIndex:0] 返回一个id。
所以我一直想如果我想调用我在 f.e. 声明的方法。 FirstViewController 类,我必须这样做:
FirstViewController *firstVC = (FirstViewController *)[self.tabBarController objectAtIndex:0];
[firstVC someMethod];
但事实证明,这是不必要的,编译器也会让我执行以下操作 - 只要我导入一个声明 someMethod 的头文件(当然它不一定会增加可读性,但无论如何):
[[self.tabBarController objectAtIndex:0] someMethod];
我完全没想到会这样。所以我假设编译器将允许在id 上调用任何方法,只要该方法在当前类范围内的任何类中声明(我的意思是,它的头文件被导入到当前类中)。如果没有导入声明someMethod 的类,编译器将抛出错误(但我必须补充一点,我在使用 ARC 时对此进行了测试。很有可能,编译器不会抱怨调用“未导入”不使用 ARC 时 id 上的方法)...
这个假设正确吗?如果可能的话,您能否提供更多关于 id 类型的信息或参考?
或者编译器是否允许在 ARC 之前调用 id(是否导入)上的任何方法,而现在对未导入方法的投诉只是 ARC 的结果?
非常感谢。
【问题讨论】:
-
实际上,使用objective-c,您可以在运行时向对象添加新方法,因此编译器无论如何都不会意识到这一点。在使用
if ([obj respondsToSelector:...调用对象之前,您应该检查对象是否支持该特定方法。
标签: objective-c ios compiler-construction