我有一个 iOS 静态库,它定义了NSOperation
客户端应该子类化以添加自己的逻辑的基类:@interface BaseClass : NSOperation
客户向管理器注册他们的子类:-[OperationManagerClass registerClass:forType:]
在管理器中,我想强制您必须注册一个子类BaseClass
不只是NSOperation
好吧,看来是断言+isSubclassOfClass:
应该完成工作。但是……事实并非如此。
@implementation OperationManagerClass
- (void)registerClass:(Class)aClass forType:(NSString *)type
{
NSAssert([aClass isSubclassOfClass:[BaseClass class]);
self.registeredClasses[type] = aClass;
}
@end
断言总是NO
,即使通过了BaseClass
.
去更高的阶级阶层怎么样?NSOperation
and NSObject
都回应YES
!
(lldb) p (BOOL)[aClass isSubclassOfClass:[BaseClass class]]
(BOOL) $0 = NO
(lldb) po aClass
BaseClass
(lldb) p (BOOL)[aClass isSubclassOfClass:[NSOperation class]]
(BOOL) $2 = YES
(lldb) p (BOOL)[aClass isSubclassOfClass:[NSObject class]]
(BOOL) $3 = YES
请注意,基操作类的使用者在 iOS 应用程序项目中进行子类化,并且OperationManagerClass
and BaseClass
位于包含的静态库中。为什么我认为这可能与isSubclassOfClass:
错了吗?由于以下...
仍在 libSharedStuff.a 中
@implementation OperationManagerClass
- (void)registerClass:(Class)aClass forType:(NSString *)type
{
// Obviously OperationManagerClass.m cannot #import "OutsideClass.h"
NSAssert([aClass isSubclassOfClass:NSClassFromString(@"OutsideClass");
self.registeredClasses[type] = aClass;
}
@end
在应用目标中
@interface OutsideClass : NSOperation
@end
@interface OutsideClassSubA : OutsideClass
@end
...产生以下结果OutsideClassSubA
传入:
(lldb) p (BOOL)[aClass isSubclassOfClass:[OutsideClass class]]
(BOOL) $0 = YES
(lldb) po aClass
OutsideClassSubA
(lldb) p (BOOL)[aClass isSubclassOfClass:[NSOperation class]]
(BOOL) $2 = YES
(lldb) p (BOOL)[aClass isSubclassOfClass:[NSObject class]]
(BOOL) $3 = YES
这里发生了什么?为什么+isSubclassOfClass:
给出错误答案?我怎样才能强制执行aClass
参数必须是我的子类BaseClass
?
Edit:
I realized the example I posted works fine after pulling the pieces into a separate Xcode workspace. I've
posted the toy source code from above https://github.com/evandelaney/StackOverflow-19883472 with a twist I left out of my original description.
我其实有two静态库(libSharedStuff.a
and libHelperSharedStuff.a
)。应用程序目标链接libSharedStuff.a
,单元测试目标取决于应用程序目标以及链接libHelperSharedStuff.a
. When BaseClass.m
是的成员both静态库目标,然后+isSubclassOfClass:
将在单元测试断言中失败。具体来说,当我通过时它会失败MockBaseClass
,它是一个子类BaseClass
这是单元测试目标的一部分。
所有这些都在上面链接的项目中进行了说明。