我有一个NSObject的子类来实现一个-(id)initWithRootElement:(MyElement *)e方法.NSXMLDocument有一个相同的方法,它采用NSXMLElement.编译时,我收到以下警告:
warning: incompatible Objective-C types 'struct MyElement *', expected 'struct NSXMLElement *' when passing argument 1 of 'initWithRootElement:' from distinct Objective-C type
在这种情况下,我正在使用Xcode 3.2.1在SnowLeopard上使用Clang + LLVM进行编译,但这也适用于Leopard和SnowLeopard上的GCC 4.2.
我不明白为什么当NSXMLDocument必须首先从NSXMLNode继承时,它为我的直接NSObject子类发出警告?它不应该知道-(id)initWithRootElement:(NSXMLElement *)e只适用于与我的课程无关的NSXMLDocument吗?我能理解我是否试图重载该方法,但我不是.请告诉我,我不会发疯...
#import <Foundation/NSAutoreleasePool.h>
#import <Foundation/NSXMLElement.h>
// Importing this here causes the warning...
// #import <Foundation/NSXMLDocument.h>
typedef NSObject MyElement;
@interface TestClass : NSObject
{
}
- (id)initWithRootElement:(MyElement *)element;
@end
@implementation TestClass
- (id)initWithRootElement:(MyElement *)element { return nil; }
@end
// ...but here it doesn't
// #import <Foundation/NSXMLDocument.h>
int main (int argc, const char * argv[])
{
NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
// No warning! Inheritance: NSXMLDocument -> NSXMLNode -> NSObject
NSXMLElement *xmlElement = [[NSXMLElement alloc] initWithName:@"foo"];
[[TestClass alloc] initWithRootElement:xmlElement];
// warning: incompatible Objective-C types 'struct MyElement *', expected 'struct NSXMLElement *' when passing argument 1 of 'initWithRootElement:' from distinct Objective-C type
MyElement *element = [[MyElement alloc] init];
[[TestClass alloc] initWithRootElement:element];
[pool drain];
return 0;
}
Run Code Online (Sandbox Code Playgroud)
bbu*_*bum 11
Objective-C不支持协变声明.
initWithRootElement:NSXMLDocument中的声明如下:
- (id)initWithRootElement:(NSXMLElement *)element;
Run Code Online (Sandbox Code Playgroud)
这与您的声明不同:
- (id)initWithRootElement:(MyElement *)element;
Run Code Online (Sandbox Code Playgroud)
因为参数类型不同.这会导致这行代码混淆(element类型为MyElement *......)
[[TestClass alloc] initWithRootElement:element];
Run Code Online (Sandbox Code Playgroud)
...因为返回类型+alloc是id,因此,编译器不知道使用哪种方法; 预期哪种类型的论点.
使用面向Apple框架的Objective-C开发代码时,经验法则是永远不要为任何给定的选择器声明不同的参数.
我有点意外,第一个案例也没有警告.它可能应该.如果您有一个相当小的测试用例,请通过http://bugreport.apple.com/提交bug 并将错误#附加到此问题(或我的答案).
| 归档时间: |
|
| 查看次数: |
3678 次 |
| 最近记录: |