饿汉式单例模式为何具备线程安全性?技术问询
Great question—this is a common point of confusion, but the answer boils down to how the JVM handles class initialization under the hood. Let's break it down step by step.
First, here's a standard eager singleton implementation for context:
public class EagerSingleton { // Instance is created immediately when the class loads private static final EagerSingleton INSTANCE = new EagerSingleton(); // Private constructor blocks external instantiation private EagerSingleton() {} public static EagerSingleton getInstance() { return INSTANCE; } }
The JVM's Built-In Thread Safety for Class Initialization
The key guarantee comes from the JVM's class loading process. When a class is first loaded into memory, it goes through a sequence of phases, and the initialization phase (where static variables are assigned and static blocks run) is thread-safe by design. Here's the critical detail:
- If multiple threads try to access a class that hasn't been initialized yet, the JVM will only let one thread execute the class's auto-generated
<clinit>()method (this method handles all static initializations). - All other threads will block and wait until the first thread finishes running
<clinit>(). - Once the class is fully initialized, every subsequent thread will skip the initialization step entirely and just use the already-created
INSTANCEvariable.
Why This Eliminates Race Conditions
In lazy initialization singletons, you have to worry about race conditions—multiple threads might enter getInstance() at the same time before the instance exists, leading to duplicate instances (unless you add explicit locks). With eager initialization:
- The instance is created before any thread can call
getInstance()—class loading happens before the class is used by any thread in your application. - There's no window for threads to race to create the instance, because the JVM has already ensured the instance is created exactly once during class initialization.
One Quick Note
You might ask: can a class be loaded multiple times? Only if you're using different class loaders. In most standard applications, though, a class is loaded exactly once per class loader instance, so your singleton instance will remain unique.
内容的提问来源于stack exchange,提问作者doctorrm

