Design pattern_1_singleton pattern

Mode singleton

Aperçu

Mode singleton, sa définition est de s'assurer qu'il n'y a qu'une seule instance d'une certaine classe et de fournir un point d'accès global.

traits

1. 不允许其他程序调用new对象
2. 在该类中创建对象
3. 对外提供一个可以让其他程序获取对象的方法

Par conséquent, lorsqu'un seul objet d'instance est nécessaire dans le système ou qu'un seul point d'accès public est autorisé dans le système et que l'instance n'est pas accessible via d'autres points d'accès à l'exception de ce point d'accès public, le mode singleton peut être utilisé

avantage

1. 节约系统资源、提高了系统效率
2. 能够严格的控制客户对它的访问

Désavantage

1. 会导致单例类的职责过重,违背了“单一职责原则”
2. 由于没有抽象类,所以拓展起来有一定的困难

atteindre

1. 私有化该类的构造函数
2. 通过new在本类中创建一个本类对象
3. 定义一个公有的方法,将在该类中所创建的对象返回

L'écriture

Le mode singleton peut être écrit de cinq manières: ①lazy, ②hungry, ③double check lock, ④static internal class, ⑤enumeration

Chinois affamé

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

avantage

Cette méthode est relativement simple à implémenter, et l'instanciation est terminée lorsque la classe est chargée, évitant le problème de synchronisation des threads

Désavantage

Comme il est instancié lorsque la classe est chargée, il n'atteint pas l'effet de chargement paresseux, ce qui signifie que je vais charger sans lui, ce qui entraînera un gaspillage de mémoire (ce gaspillage peut être ignoré, donc cette méthode est également recommandée )
Si l'initialisation elle-même dépend de certaines autres données, il est difficile de s'assurer que les autres données sont prêtes avant d'être initialisées

Transformation

public class Singleton{
    
    
	private static Singleton instance = null;
	static{
    
    
	instance = new Singleton();
	}
	private Singleton(){
    
    }
	public static Singleton getInstance(){
    
    
		return instance;
	}
}

Un homme paresseux

Ecrire un [thread n'est pas sûr et indisponible]

public class Singleton{
    
    
	private static Singleton instance = null;
	private Singleton(){
    
    }
	public static Singleton getInstance(){
    
    
		if(instance == null) instance = new Singleton();
		return instance;
	}
}

Cette façon d'écrire entraînera des problèmes de sécurité des threads et peut créer deux objets en même temps

Méthode d’écriture deux [sécurité des threads, faible efficacité, non recommandée]

public class Singleton{
    
    
	private static Singleton instance = null;
	private Singleton(){
    
    }
	public static synchronized Singleton getInstance(){
    
    
		if(instance == null) instance = new Singleton();
		return instance;
	}
}

L'efficacité d'exécution est trop faible. Lorsque chaque thread souhaite obtenir une instance de la classe, la méthode getInstance () doit être exécutée de manière synchrone. Cette méthode ne doit être exécutée qu'une seule fois, puis vous souhaitez obtenir le retour direct.

Amélioration [Thread is not safe and not available]

public class Singleton{
    
    
	private static Singleton instance = null;
	private Singleton(){
    
    }
	public static Singleton getInstance(){
    
    
		if(instance == null) {
    
    
			synchronized(Singleton.class){
    
    
				instance = new Singleton();
			}
		}
		return instance;
	}
}

Il peut y avoir un deuxième thread entrant dans le bloc d'instruction if. Une fois le premier thread exécuté, le deuxième thread créera à nouveau un objet, donc le grand dieu a écrit le verrou de double vérification paresseux.

Vérifier le verrouillage [recommandé]

public class Singleton{
    
    
	/**
	* 懒汉式变种,属于懒汉式中最好的写法,
	* 保证了:延迟加载和线程安全
	*/
	private static Singleton instance = null;
	private Singleton(){
    
    }
	public static Singleton getInstance(){
    
    
		if(instance == null) {
    
    
			synchronized(Singleton.class){
    
    
				if(instance == null) instance = new Singleton();
			}
		}
		return instance;
	}
}

Nous effectuons deux if (instance == null checks, afin de garantir la sécurité des threads), et nous retournerons l'objet d'instance directement lorsque nous y accèderons plus tard

avantage

Sécurité du fil, chargement paresseux, haute efficacité

Désavantage

Le code ci-dessus semble parfait, mais en fait il y a encore un léger défaut: la classe a été appelée par d'autres threads avant d'être chargée.

Améliorer

La méthode ci-dessus a été améliorée. Ajoutez simplement le mot-clé volatile à l'instruction d'instance. La fonction du mot-clé volatile est d'interdire le réarrangement des instructions, de sorte que l'opération de lecture ne soit pas autorisée tant que l'affectation n'est pas terminée.

public class Singleton{
    
    
	private static volatile Singleton instance = null;
	private Singleton(){
    
    }
	public static Singleton getInstance(){
    
    
		if(instance == null) {
    
    
			synchronized(Singleton.class){
    
    
				if(instance == null) instance = new Singleton();
			}
		}
		return instance;
	}
}

Classe interne statique [recommandé]

public class singleton{
    
    
	private Singleton(){
    
    }
	private static class SingletonHolder{
    
    
		private static final Singleton INSTANCE = new Singleton();
	}
	public static final Singleton getInstance(){
    
    
        return SingletonHolder.INSTANCE;
    }
}

Lorsque la classe Singleton est chargée, elle ne sera pas instanciée, mais lorsque la méthode getInstance est appelée, la classe SingletonHohder sera chargée pour terminer l'instanciation du Singleton.
Pourquoi pouvons-nous garantir la sécurité des fils?
Les propriétés statiques de la classe ne seront initialisées que lors du premier chargement de la classe. La machine virtuelle Java nous aide à garantir la sécurité du thread. Lorsque la classe est initialisée, les autres threads ne peuvent pas entrer

avantage

线程安全,延迟加载,效率高

Énumération 【Hautement recommandé】

public enum SingletonEnum{
    
    
	INSTANCE;
	private SingletonEnum(){
    
    }
	public void method(){
    
    
		
	}
}

L'écriture de l'énumération est très simple, la méthode d'accès SingletonEnum.INSTANCE où INSTANCE est la référence de type SingletonEnum, vous pouvez appeler la méthode dans l'énumération lorsque vous l'obtenez

Blog de référence

https://www.cnblogs.com/pony1223/p/7608955.html
http://blog.csdn.net/dmk877/article/details/50311791
https://www.cnblogs.com/dongyu666/p/6971783. html

Je suppose que tu aimes

Origine blog.csdn.net/BrightZhuz/article/details/108904829
conseillé
Classement