objective-c 目标 c isKindOfClass 误解?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/2045561/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Objective c isKindOfClass missunderstanding?
提问by Vitek
I have following structure of objects:
我有以下对象结构:
Animal, Dog and Cat. As You expect Dog and Cat are inherited from Animal.
动物、狗和猫。正如您所期望的那样 Dog 和 Cat 是从 Animal 继承而来的。
And I've a farm class:
我有一个农场课:
@implementation AnimalFarm
-(Animal*) createAnimal:(AnimalType)type{
switch (type) {
case CAT:
return [Cat new];
case DOG:
return [Dog new];
default:
return [Animal new];
}
}
@end
and I tried to unit test:
我尝试进行单元测试:
AnimalFarm *farm = [AnimalFarm new];
Animal *dog = [farm createAnimal:DOG];
Animal *cat = [farm createAnimal:CAT];
STAssertTrue([cat isMemberOfClass:[Cat class]],@"cat is not a cat!");
STAssertTrue([dog isMemberOfClass:[Dog class]],@"Dog is not a dog!");
STAssertTrue([cat isKindOfClass:[Animal class]],@"Cat is not an animal!");
STAssertTrue([dog isKindOfClass:[Animal class]],@"Cat is not an animal!");
Implementation of classes:
类的实现:
@interface Cat : Animal {
}
@end
@implementation Cat
-(NSString*) say{
return @"miau";
}
@end
Implementation of dog is similar.
dog 的实现是类似的。
but neither isKindOfClass or isMemberOfClass worked as I expected....
但 isKindOfClass 或 isMemberOfClass 都没有按我预期的那样工作......
Am I missing something?
我错过了什么吗?
When I use IFs instead of switch then everything goes well ... but what is the difference?
当我使用 IF 而不是 switch 时,一切都很顺利……但有什么区别?
Implementation of createAnimal which works:
工作的 createAnimal 的实现:
-(Animal *) createAnimal:(AnimalType)type {
if (type == DOG) {
return [Dog new];
} else if (type == CAT) {
return [Cat new];
} else {
return [Animal new];
}
回答by dreamlax
isMemberOfClass:will only return YESif the instance's class is exactly the same, however isKindOfClass:will return YESif the instance's class is the same, or a subclass of the given class.
isMemberOfClass:仅YES当实例的类完全相同时isKindOfClass:才会返回,但是YES如果实例的类相同或给定类的子类,则返回。
For example this will output No!:
例如,这将输出No!:
BOOL result = [[NSMutableArray array] isMemberOfClass:[NSArray class]];
NSLog (@"%@", result? @"Yes!" : @"No!");
But this will output Yes!:
但这将输出Yes!:
BOOL result = [[NSMutableArray array] isKindOfClass:[NSArray class]];
NSLog (@"%@", result? @"Yes!" : @"No!");
This is because an NSMutableArray is a kindof NSArray, but it isn't a member of the NSArray class (otherwise it wouldn't be an NSMutableArray).
这是因为 NSMutableArray 是一种NSArray,但它不是 NSArray 类的成员(否则它不会是 NSMutableArray)。
Throughout Foundation and Cocoa, there are a number of "class clusters". You can read more about this in the documentation on Apple's developer web site. Due to the nature of class clusters, if you create perhaps an NSStringobject, it may fail the isMemberOfClass:[NSString class]test.
在 Foundation 和 Cocoa 中,有许多“类集群”。您可以在Apple 开发人员网站上的文档中阅读更多相关信息。由于类簇的性质,如果您创建一个NSString对象,它可能无法通过isMemberOfClass:[NSString class]测试。
If neither isKindOfClass:or isMemberOfClass:is returning the correct value, see what class the actual object is with
如果两者都没有isKindOfClass:或isMemberOfClass:没有返回正确的值,请查看实际对象所属的类
NSLog(@"cat class = %@, dog class = %@", [cat className], [dog className]);
If these are returning anything other than what they are supposed to, then there is a problem with your farm class.
如果这些返回的东西超出了它们的预期,那么你的农场课程就有问题。
回答by Dave DeLong
Your problem lies elsewhere.
你的问题在别处。
I created your Animal, Dog, and Catclasses, and the four cases you have above passed. For reference, here is my code: http://pastie.org/774468
我创建了您的Animal、Dog和Cat类,以及您上面通过的四个案例。作为参考,这是我的代码:http: //pastie.org/774468
It outputs:
它输出:
2010-01-11 19:45:10.259 EmptyFoundation[83698:a0f] [cat isMemberOfClass:[Cat class]] PASSED
2010-01-11 19:45:10.265 EmptyFoundation[83698:a0f] [dog isMemberOfClass:[Dog class]] PASSED
2010-01-11 19:45:10.265 EmptyFoundation[83698:a0f] [cat isKindOfClass:[Animal class]] PASSED
2010-01-11 19:45:10.273 EmptyFoundation[83698:a0f] [dog isKindOfClass:[Animal class]] PASSED
EDIT:
编辑:
I suppose there was a slight possibility that your AnimalFarmobject was the source of the error, but I just tried creating the animal objects that way and got the same results (code: http://pastie.org/774480):
我认为您的AnimalFarm对象有可能是错误的根源,但我只是尝试以这种方式创建动物对象并得到相同的结果(代码:http: //pastie.org/774480):
2010-01-11 19:51:35.144 EmptyFoundation[83741:a0f] [cat isMemberOfClass:[Cat class]] PASSED
2010-01-11 19:51:35.156 EmptyFoundation[83741:a0f] [dog isMemberOfClass:[Dog class]] PASSED
2010-01-11 19:51:35.157 EmptyFoundation[83741:a0f] ![ant isMemberOfClass:[Cat class]] PASSED
2010-01-11 19:51:35.157 EmptyFoundation[83741:a0f] [cat isKindOfClass:[Animal class]] PASSED
2010-01-11 19:51:35.157 EmptyFoundation[83741:a0f] [dog isKindOfClass:[Animal class]] PASSED
2010-01-11 19:51:35.158 EmptyFoundation[83741:a0f] [ant isKindOfClass:[Animal class]] PASSED
EDIT #2:
编辑#2:
Based on your observation that an if...else if statement works but the switch statement does not, I modified the code I posted above to use a switch statement.... and it worked just fine. So my comment/question stands: In your if/switch statements, you're using these constants DOGand CAT. Where are those defined?
根据您的观察,if...else if 语句有效但 switch 语句无效,我修改了上面发布的代码以使用 switch 语句......并且它工作得很好。所以我的评论/问题是:在你的 if/switch 语句中,你正在使用这些常量DOG和CAT. 那些在哪里定义的?
回答by Hyman
You are missing breaks, that's why your switch isn't working. It should look like this.
您错过了休息时间,这就是您的开关无法正常工作的原因。它应该是这样的。
switch (type) {
case CAT:
return [Cat new];
break;
case DOG:
return [Dog new];
break;
default:
return [Animal new];
break;
}

