问题
I have a singleton that takes a few seconds to instantiate. It makes the UI freezes. So I'm planning to make the getInstance()
method asynchronous. Is writing the following code a common practice?
/*
* The singleton class
*/
public class Singleton {
private static volatile Singleton instance;
public static Observable<Singleton> getInstance(Context context) {
return Observable.fromCallable(() -> {
synchronized (Singleton.class) {
if (instance == null)
instance = new Singleton(context.getApplicationContext());
}
return instance;
});
}
private Singleton(Context context) {
// long running process
}
// ...
}
/*
* The UI class
*/
public class UI extends Activity {
private Singleton singleton;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Singleton.getInstance(this)
.subscribeOn(Schedulers.io())
.observeOn(AndroidSchedulers.mainThread())
.subscribe(result -> {
UI.this.singleton = result
})
}
public void onButtonClick(View v) {
if (singleton != null)
singleton.someMethod();
}
}
If it's not, why isn't it and what's the better solution?
回答1:
What you want is to cache the value returned from the callable, so the next time you call subscribe you do not want to execute the Callable again. For that use cache operator.
Single<Integer> cachedValue = Single.fromCallable(() -> {
Thread.sleep(3000);
return 5;
}).cache();
cachedValue.subscribe(e -> System.out.println(System.currentTimeMillis() + ": " + e));
cachedValue.subscribe(e -> System.out.println(System.currentTimeMillis() + ": " + e));
You'll notice that the time for the second call is too close to the first one. At least < 3000 MS.
回答2:
Check this Safe Singleton. Enums are the way to make it safe singleton
来源:https://stackoverflow.com/questions/59484133/is-it-a-good-idea-to-make-singletons-getinstance-method-asynchronous-by-makin