Types, advantages and disadvantages of Android singleton mode

Posted by trilbyfish on Thu, 23 Sep 2021 11:37:54 +0200

catalogue

Singleton mode definition:

Core principle of singleton mode:

What should be paid attention to when using singleton mode

Single case of hungry man

Lazy single case

DCL single case (Double Check Lock)

Static internal class singleton (recommended)

Enumeration singleton

Container single example

last

How to ensure thread safety when static internal classes:

Singleton mode definition:

1. Ensure that a class has only one instance, and instantiate it by itself and provide this instance to the whole system.

Core principle of singleton mode:

1. Privatization of constructors;
2. Obtain the only instance through static method;

What should be paid attention to when using singleton mode

1. Resource consumption of the object;
2. Redundant synchronization;
3. Thread safety;

Single case of hungry man

public class HungrySingleTone {

    private static HungrySingleTone instance = new HungrySingleTone();

    private HungrySingleTone() {
    }

    public static HungrySingleTone getInstance() {
        return instance;
    }

}

advantage:

Disadvantages: when the application runs, it is instantiated when it is not necessary, which does not save memory space

Lazy single case

public class LazySingleTone {

    private static LazySingleTone instance;

    private LazySingleTone() {
    }

    /**
     * Initialize instance when getting instance
     * @Description Consider multiple threads calling getInstance concurrently, and add the synchronized keyword
     * @return
     */
    public static synchronized LazySingleTone getInstance() {
        if (instance == null) {
            instance = new LazySingleTone();
        }
        return instance;
    }

    //Each getInstance is subject to synchronization lock overhead, which is not necessary for getinstances,
    //Instead, a synchronization lock is required for the new instance
}

Advantages and disadvantages:

Advantages: compared with the hungry man singleton mode, it can only be instantiated when used

Disadvantages: redundant synchronization. In order to ensure the uniqueness of a single instance object in multiple threads, getInstance() adds the synchronized keyword, and the synchronization overhead will be incurred every time the getInstance method is called.

DCL single case (Double Check Lock)

public class DclSingleTone {

    private static DclSingleTone instance;

    private DclSingleTone() {
    }

    /**
     * Every getInstance
     *
     * @return
     * @Description Double judgment to achieve the extreme of single case mode
     */
    public static DclSingleTone getInstance() {
        //It has been instantiated, and no synchronization lock is required
        if (instance == null) {
            synchronized (DclSingleTone.class) {
                //For the first multi-threaded queuing, the initial instance still needs to judge whether it is new or not internally
                if (instance == null) {
                    instance = new DclSingleTone();
                }
            }
        }
        return instance;
    }
}

Advantages: instantiation during use, thread safety, and no redundant synchronization

Disadvantages: (when used in complex concurrent scenarios or versions lower than JDK6, Dcl may fail. This scenario is not well understood)

Static internal class singleton (recommended)

public class StaticInnerSingleTone {

    private StaticInnerSingleTone() { }

    private static class InnerSingleToneHolder {
        private static final StaticInnerSingleTone instance = new StaticInnerSingleTone();
    }

    public static StaticInnerSingleTone getInstance() {
        return InnerSingleToneHolder.instance;
    }

    //Only when getInstance is called for the first time can instance be initialized, which can not only ensure thread safety, but also ensure the uniqueness of singleton object, but also delay
    //Singleton object instantiation, so this is the recommended singleton pattern implementation.

}

Advantages: instantiation during use, thread safety, and no redundant synchronization

Disadvantages:

Enumeration singleton

public enum SingletomeEnum {
    INSTANCE;
    //public method...
}

Advantages: simple writing

Disadvantages: (does enum occupy too much memory...)

Container single example

public class SingletoneManager {
    
    private static Map<String,Object> objMap = new HashMap<String,Object>();
    
    private SingletoneManager() {}
    
    public static void registerService(){
        
    }
    
    public static Object getService(String key){
        
    }
}

Advantages: multiple singleton types are injected into a singleton management class to reduce the use cost, hide the specific implementation and reduce the coupling degree. (container singleton used by getSystemService() of system context)

Disadvantages: look at the initial memory consumption value is not worth

last

How to ensure thread safety when static internal classes:

Features of static internal classes: static internal classes do not need to be loaded when external classes are loaded. If they are not loaded, they do not occupy memory. (delayed loading) static internal classes are loaded only when external classes call getInstance method. Static attributes ensure global uniqueness, and static variable initialization ensures thread safety. Therefore, the synchronized keyword is not added to the methods here (the JVM ensures that the initialization of a class is locked synchronously under multithreading)

Topics: Android Singleton pattern