我正在开发一个主要是Objective-C但正在转换为Swift的现有大型代码库。
新的类正在Swift中实现,但是其中一些类需要从现有的ObjC代码中进行访问。为了遵循ObjC和Swift的最佳实践,新类没有前缀,但是为ObjC定义了前缀。
/**
Create contrived class that is named XXClassA in ObjC and ClassA in Swift.
*/
@objc(XXClassA) class ClassA: NSObject {
let foo = "bar"
}
到目前为止,这一直很好。 Swift代码使用
ClassA()
,而ObjC使用[[XXClassA alloc] init]
。一旦删除了所有引用XXClassA的ObjC代码,就可以从Swift类中删除@objc(XXClassA)
。不幸的是,如果您有一个ObjC类引用XXClassA,然后Swift代码尝试在ClassA内部使用该新类,则此操作将失败。
假设我创建了一个名为
XXClassC
的ObjC类,它使用XXClassA
实例化了自己(实际上是Swift类ClassA
)//
// XXClassC.h
//
#import <Foundation/Foundation.h>
NS_ASSUME_NONNULL_BEGIN
@class XXClassA;
@interface XXClassC : NSObject
-(instancetype)initWithA:(XXClassA *)classA;
@end
NS_ASSUME_NONNULL_END
循环引用现已到位。如果尝试从ClassA内部使用XXClassC,则初始化程序不可用。
如果我改用ClassA来重新定义,一切都会好起来的。
class XXClassA: NSObject {
let foo = "bar"
}
我知道为什么会发生这种情况,并且已经有了解决方法,但是我想继续使用这种带前缀的ObjC类的模式。关于如何避免循环导入,但又保持命名约定的任何想法?
完整的代码示例在这里:https://gist.github.com/justAnotherDev/78483f9d94e40fd90c38
最佳答案
我有同样的问题。我的解决方法是:
typealias ClassA = XXClassA
。 使用这种模式,当最后一个objc依赖项消失时,至少很容易删除前缀。