swift – 具有参数的Singleton和init
我想在我的类中使用具有私有init参数的单例模式.它还有一个名为setup的类函数,用于配置和创建共享实例.我的目标c代码是:
@interface MySingleton: NSObject + (MySingleton *)setup:(MyConfig *)config; + (MySingleton *)shared; @property (readonly,strong,nonatomic) MyConfig *config; @end @implementation MySingleton static MySingleton *sharedInstance = nil; + (MySingleton *)setup:(MyConfig *)config { static dispatch_once_t onceToken; dispatch_once(&onceToken,^{ sharedInstance = [[self alloc] initWithConfig:config]; }); // Some other stuff here return sharedInstance; } + (MySingleton *)shared { if (sharedInstance == nil) { NSLog(@"error: shared called before setup"); } return sharedInstance; } - (instancetype)initWithConfig:(RVConfig *)config { self = [super init]; if (self) { _config = config; } return self; } @end 我被困在Swift: class Asteroid { var config: ASTConfig? // This actually should be read-only class func setup(config: ASTConfig) -> Asteroid { struct Static { static let instance : Asteroid = Asteroid(config: config) } return Static.instance } class var shared: Asteroid? { // ??? } private init(config: ASTConfig) { self.config = config } } 我认为我仍然以客观的方式思考,不能用快速的方法来计算出来.任何帮助?
您的Objective-C代码的字面翻译可能是:
private var _asteroidSharedInstance: Asteroid! class Asteroid { private var config: ASTConfig? class func setup(config: ASTConfig) -> Asteroid { struct Static { static var onceToken: dispatch_once_t = 0 } dispatch_once(&Static.onceToken) { _asteroidSharedInstance = Asteroid(config: config) } return _asteroidSharedInstance } class var sharedInstance: Asteroid! { // personally,I'd make this `Asteroid`,not `Asteroid!`,but this is up to you if _asteroidSharedInstance == nil { println("error: shared called before setup") } return _asteroidSharedInstance } init(config: ASTConfig) { self.config = config } } 或者,在Swift 1.2中,您可以消除静态结构并简化安装程序: private static var setupOnceToken: dispatch_once_t = 0 class func setup(config: ASTConfig) -> Asteroid { dispatch_once(&setupOnceToken) { _asteroidSharedInstance = Asteroid(config: config) } return _asteroidSharedInstance } 这真的不是一个单身人士. (我怀疑你知道这一点,但我提到为了未来读者的利益).通常单例可以在首次使用的任何地方进行实例化.这是一个场景,它只在一个特定的地方进行实例化和配置,您必须注意在尝试在其他地方使用它.这是非常好奇的做法.我们失去了一些单例功能,但仍然遭受所有传统的单身限制. 很明显,如果你确定,那没关系.但是,如果你有趣的替代品,两个人就跳出来: >使这个真正的单例:您可以通过在init方法中移动ASTConfig的实例化来实现此目的(消除在使用sharedInstance之前必须调用setup的依赖关系).然后你可以退出设置,只要像你一样使用你的单身.所产生的实现也大大简化.它减少到像: class Asteroid { static let sharedInstance = Asteroid() private let config: ASTConfig init() { self.config = ASTConfig(...) } } 显然,我怀疑恶魔是在这个ASTConfig对象的细节,但是如果你可以做一个正确的单例执行,你可以看到这是更简单(特别是在Swift 1.2).而且上面消除了设置vs sharedInstance问题.消除私人全球.一切都简单一些 话虽如此,我认为你有令人信服的理由这样做.也许有一些关键原因,您必须将ASTConfig对象传递给安装方法,而不是仅在Asteroid类的初始化中实例化. 我只是觉得有必要指出,一个适当的单例将是非常好的(两者都更简单的实现和消除理论竞争条件). 您已经指定您要手动将Asteroid设置在前面,所以让我们正式确定这种关系,并消除单身人士介绍的许多结构性缺陷(参见What’s Alternative to Singleton或谷歌“单身人士”). 不要误会我我假设你有令人信服的理由按照你的方式做到这一点,如果目前的实现方式适用于你,那没关系.但这是一个非常好奇的做法,在这种做法中,您不用享受所有的好处就承担单身人士的理论责任. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |