Java Design Patterns-thread-safe single-piece mode

Source: Internet
Author: User
Tags volatile

A single-piece mode, also known as a singleton mode, is used to create unique objects that can have only one instance.

The class diagram of a single-piece pattern is the simplest of all patterns in the class diagram--only one class. Although the single-piece mode is simple from the point of view of class design, there are still some problems in the implementation, this article focuses on the analysis and solution.

The simplest implementation of the single-piece mode, the code is as follows:

1 /**2 * Created by Mcbye King on 2016/10/23.3  */4  Public classSingleton {5     Private StaticSingleton Singleton;6     PrivateSingleton () {}7     Public StaticSingleton Getsingleton () {8         if(Singleton = =NULL){9Singleton =NewSingleton ();Ten         } One         returnSingleton; A     } -}

Combined with the above code, the single-piece mode is briefly elaborated.

In a single-piece mode, a static variable is used to record only instances of the Singleton class. The constructor is declared private and can only be called from within the Singleton class. To instantiate the class, it calls the Getsingleton method, where it instantiates and returns the instance. There is also a "lazy instantiation" idea, where, if we don't need this instance, it will never happen. In practice, of course, you can add other behaviors to this class.

It seems that this is all a single piece mode, because the single-piece mode is too simple, but if careful, there are many problems.

Think of a question, what if there are two or more threads calling to use the Singleton class above?

Since there is no protection for this singleton class external interface Getsingleton () method, each thread can call to this function at the same time, it is possible for several threads to access this method at the same time, and to make the judgment of if (singleton = = null), because it is simultaneous, So what you see is an singleton that has not been instantiated, and then there are several singleton instance objects appearing--which completely violates the original intent of the single-piece model. --If you say it's a coincidence, yes, but it does actually exist, there's a big chance of a major bug.

Next we consider how to solve this problem.

1, as long as the Getsingleton () into a synchronous (synchronized) method , multi-threaded disaster can be solved almost, the following example:

/*** Created by Mcbye King on 2016/10/23.*/ Public classSingleton {Private StaticSingleton Singleton; PrivateSingleton () {} Public Static synchronizedSingleton Getsingleton () {if(Singleton = =NULL) {Singleton=NewSingleton (); }        returnSingleton; }}

By adding the Synchronized keyword to the Getsingleton () method, we force each thread to wait for another thread to leave the method before entering this method. This means that two threads are not allowed to enter this method at the same time.

2, adding the Synchronized method undoubtedly solves the synchronization problem , but obviously degrades performance, which in turn leads to another problem. If performance can be sacrificed, that is, the performance of the Getsingleton () method has little impact on the application, it is not wrong to use the method above. Otherwise, the "lazy instantiation" becomes "eager" to create an instance of the.

/***/Publicclass  Singleton    {privatestatic  New  Singleton ();     Private Singleton () {}      Public Static synchronized Singleton Getsingleton () {        return  Singleton;    }}

The creation of a single piece in the static initializer guarantees thread safety. Of course, this approach works for applications that always create and use a single instance, or that the burden of creating and running is not too heavy.

3, a relatively better way is: with "Double check lock", in Getsingleton () to reduce the use of synchronization .

Take a look at the code:

/*** Created by Mcbye King on 2016/10/23.*/ Public classSingleton {Private volatile StaticSingleton Singleton; PrivateSingleton () {} Public StaticSingleton Getsingleton () {if(Singleton = =NULL){            synchronized(Singleton.class){                if(Singleton = =NULL) {Singleton=NewSingleton (); }            }        }        returnSingleton; }}

In the Getsingleton () instantiation method of the above code, the instance is checked first, and if it does not exist, it enters the synchronization chunk, and only the first time the code in the synchronized chunk is completely executed.

The volatile keyword ensures that when the singleton variable is initialized to an singleton instance, multiple threads handle the singleton variable correctly.

If performance is the focus of consideration, the above approach can help greatly reduce the time spent on Getsingleton (). --provided that it is in Java 5 and later in the Java version.

  

Java Design Patterns-thread-safe single-piece mode

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.