[iOS, swift] thread-safety 한 싱글톤 사용은?

lazily initialized 하고 멀티코어를 고려한 Thread-Safe 방법

Clint Jang
4 min readOct 17, 2018

간단합니다. 기존에 하시던 방법 그대로 일 것 입니다.

싱글톤(Singleton) 을 생성해주는 방법은

static 프로퍼티에 인스턴스를 생성해주면 끝입니다.

그리고 한가지 더 … 추가적으로 다른 곳에서 생성하지 못하도록(private init() {} )아래의 방법으로 사용하면..

class Singleton {
static let shared = Singleton()
private init() {}
}

간결하고, 가장 적절한 방법인 것 같습니다.

(역시 스위프트!!)

Swift 3.0 부터는 dispatch_once는 Swift에서 더 이상 사용할 수 없다고 했습니다. 사용할 필요가 없도록 한거죠.

Dispatch

  • The free function dispatch_once is no longer available in Swift. In Swift, you can use lazily initialized globals or static properties and get the same thread-safety and called-once guarantees as dispatch_once provided.

전역변수를 사용하여 인스턴스를 생성하면…

사용 시점에 초기화(lazily initialized) 되고, GCD의 dispatch_once도 자동 적용 되어 인스턴스가 생성되어 가장 코드가 깔끔한 Thread-Safe한 방법이 되는 것 같습니다.

GCD는 멀티코어 프로세서를 위한 Thread 프로그래밍을 OS에서 자동으로 관리하고 배분해 주는 방법이라 Apple에서 가장 사용을 권하는 Concurrency 처리 방법이죠.

그리고 아래 스위프트 블로그에도 Global Variables 마지막 부분을 보면 .. 해당 내용이 역시 설명되어있습니다.

...The lazy initializer for a global variable (also for static members of structs and enums) is run the first time that global is accessed, and is launched as dispatch_once to make sure that the initialization is atomic. This enables a cool way to use dispatch_once in your code: just declare a global variable with an initializer and mark it private....

java에서의 가장 완벽하다고 하는 LazyHolder 와도 위의 swift에서의 방법과 같은 수준의 싱글톤 패턴을 사용하는 방법이 아닌 가 싶습니다.😀

public class Singleton {  
private Singleton() {}
public static Singleton getInstance() {
return LazyHolder.instance;
}
private static class LazyHolder {
private static final Singleton instance = new Singleton();
}
}

불필요한 메모리 생성을 피하기 위해 초기화를 미루고(lazily initialized), LazyHoder 클래스가 참조하는 시점에 초기화 하는 것은 JVM 에서 알아서 최적의 thread-safe하면서 성능도 보장해주도록 생성해주는 방법이죠.

(volatile, synchronized 가 불필요한 최고의 방법)

좋은 하루되세요. 🙇

--

--