Maison > Java > javaDidacticiel > Qu'est-ce que le mode de verrouillage à double vérification Java

Qu'est-ce que le mode de verrouillage à double vérification Java

WBOY
Libérer: 2023-05-19 15:29:49
avant
1513 Les gens l'ont consulté

Cause

J'ai rencontré un tel problème lors de la détection de code statique PMD sur le projet

Les objets partiellement créés peuvent être renvoyés par le modèle de verrouillage à double vérification lorsqu'il est utilisé en Java. Un JRE d'optimisation peut attribuer une référence à la variable baz. avant d'appeler le constructeur de l'objet vers lequel pointe la référence.

Remarque : avec Java 5, vous pouvez faire fonctionner le verrouillage à double vérification, si vous déclarez la variable comme volatile. renvoie un objet incomplètement initialisé. Certaines personnes peuvent douter du concept d'objets partiellement initialisés, veuillez continuer à analyser

Qu'est-ce que le mode de verrouillage à double vérification

<code>public static Singleton getSingleton() {<br>    if (instance == null) {                        <br>        synchronized (Singleton.class) {<br>            if (instance == null) {                 <br>                instance = new Singleton();<br>            }<br>        }<br>    }<br>    return instance ;<br>}</code> 
Copier après la connexion
Nous voyons que instance == null est jugé à la fois à l'intérieur et à l'extérieur du bloc de code synchronisé. les threads peuvent entrer le jugement if en dehors du bloc de code synchronisé en même temps. Si aucun jugement nul n'est effectué à l'intérieur du bloc de code synchronisé, plusieurs instances peuvent être initialisées.

Le problème

Cette façon d'écrire semble parfaite, mais elle est problématique, ou elle ne garantit pas qu'elle sera parfaite. La raison principale est que instance = new Singleton(); n'est pas une opération atomique.

La création d'un objet peut être divisée en trois parties :

<code>1.分配对象的内存空间<br>2.初始化对象<br>3.设置instance指向刚分配的内存地址<br>当instance指向分配地址时,instance是不为null的</code> 
Copier après la connexion

Cependant, entre les étapes 2 et 3, elle peut être réorganisée, ce qui fait que l'ordre de création des objets devient 1-3-2. Imaginez un scénario :
Thème A pour le. Créez l'objet Singleton pour la première fois, et l'ordre de création de l'objet est 1-3-2 ;

Après avoir alloué de la mémoire à l'instance, un thread B vient et appelle la méthode getSingleton()

À ce moment, cette instance est jugée. == null, et on constate que l'instance n'est pas Not null.
Mais notez que l'instance n'a pas initialisé l'objet pour le moment et que le thread B renverra l'objet non initialisé. Des problèmes peuvent survenir lorsque le thread B utilise l'instance. Il s'agit du problème du verrouillage à double vérification.

Utiliser volatile

Pour les problèmes ci-dessus, nous pouvons résoudre le problème ci-dessus en déclarant l'instance comme volatile

<code>public class Singleton{<br>    private volatile static Singleton instance;<br>    public static Singleton getSingleton() {<br>        if (instance == null) {                        <br>            synchronized (Singleton.class) {<br>                if (instance == null) {                 <br>                    instance = new Singleton();<br>                }<br>            }<br>        }<br>        return instance ;<br>    }<br>}</code> 
Copier après la connexion

Mais elle doit être utilisée dans la version JDK5 ou supérieure.

Classe interne statique

<code>public class Singleton {  <br>    private static class SingletonHolder {  <br>        private static final Singleton INSTANCE = new Singleton();  <br>    }  <br>    private Singleton (){}  <br>    public static final Singleton getInstance() {  <br>        return SingletonHolder.INSTANCE; <br>    }  <br>}</code>
Copier après la connexion
La méthode d'écriture actuellement recommandée consiste à utiliser des classes internes statiques, qui peuvent réaliser un chargement paresseux sans problèmes de sécurité des threads. Et cela réduit les frais généraux de synchronisation.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Étiquettes associées:
source:yisu.com
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal