J'ai beaucoup lu sur les dangers de la double verrouillage vérifiée et j'essaierais de l'écart, mais avec cela dit, je pense qu'ils font une lecture très intéressante.
Je lisais cet article de Joe Duffy À propos de la mise en œuvre du singleton avec un verrouillage double vérifié: http://www.bluebytesoftware.com/blog /Permalink ,Guid 543d89ad-8d57-4A51-B7C9-A821E3992BF6.aspx P>
et la solution (variante de) Il semblait proposer est-ce: p> } P> Ma question est que cela n'a pas encore le danger d'écriture de la réorganisation? Spécifiquement, ces deux lignes: p> si ces écritures sont inversées, un autre thread peut toujours lire NULL. P> P>
3 Réponses :
Je pense que la clé est dans l'article lié ( http://msdn.microsoft.com /en-us/magazine/cc163715.aspx#ss5 ). Plus précisément que le modèle de mémoire MS-Mise en œuvre 2.0 a la propriété suivante: p>
Écrit ne peut pas passer au-delà des autres écrit du même fil. P> blockQuote>
Duffy mentionne que beaucoup de travail a été fait pour soutenir cela sur l'IA-64: P>
Nous accomplissons cela en assurant des écritures ont une sémantique «libération» sur IA-64, via l'instruction ST.REL. Un seul st.rel X garantit que toutes les autres charges et magasins menant à son exécution (dans le flux d'instructions physiques) doivent être apparues survenus sur chaque processeur logique au moins par la nouvelle valeur de X's X devient visible à un autre processeur logique. Les charges peuvent être données «Acquérir» sémantique (via l'instruction LD.ACQ), ce qui signifie que toutes les autres charges et magasins qui se produisent après qu'un LD.ACQ X ne peut sembler avoir eu lieu avant la charge. P> blockQuote>
Notez que Duffy mentionne également qu'il s'agit d'une garantie spécifique aux États membres - ce n'est pas une partie de la spécification ECMA (au moins comme de l'écriture de l'article en 2006). Donc, Mono pourrait ne pas être aussi gentil. P>
Excellente réponse! Je m'excuse et merci de mieux avoir lu que je le fais =).
Selon http://msdn.microsoft.com/en-us/ Bibliothèque / EE817670.ASPX
Un singleton comme est garanti pour être thread-coffre-fort p> Le cadre garantit en interne la sécurité du fil sur l'initialisation de type statique. [..] Dans le cadre lui-même, plusieurs classes utilisent ce type de singleton, bien que le nom de propriété utilisé soit appelé valeur à la place. Le concept est exactement le même. P>
blockQuote> p>
Vous n'avez pas répondu à la question.
Oh je vois. Je pense que les deux lignes sont sûres (par elles-mêmes, étant gardées par une serrure appropriée sur un singleton). Cependant, la vérification volatile / non volatile de initialisée code> semble fragile. Est-ce ce que vous demandiez?
Votre réponse concerne les constructeurs statiques étant le fil sûr. La question concerne une méthode particulière de verrouillage à double contrôle. Sujet totalement différent. -1
Commentaires initiaux forts> Je ne pense pas nécessairement que l'auteur de cet article proposait réellement que cette variation du modèle de verrouillage à double vérification soit utilisée en soi. Je pense qu'il venait de souligner que c'est une variation qui pourrait être envisagée par un développeur naïf pour lutter contre le problème dans le contexte des types de valeur. P> Types de valeur ne peut évidemment pas stocker L'utilisation de null code> Les valeurs de sorte qu'une autre variable doit être utilisée pour signaler l'achèvement de l'initialisation. L'auteur mentionne tout cela et parle ensuite de manière confusion sur la lecture
instance code> comme
null code>. Vraisemblablement, l'auteur pensait à un vraiment em> développeur naïf qui a utilisé cette variation mal sur les types de valeur à une fois, puis a continué à l'appliquer, de manière incorrecte pour les types de référence. Dans le cas d'une valeur de type de valeur, un thread pourrait lire et utiliser un
struct code> avec des initialisations de champ par défaut lorsque cela n'a pas été prévu. Dans le cas des types de référence, un thread pourrait lire et utiliser
NULL code> instance. P>
thread.volatileread code> était la proposition de l'auteur de corriger cette variation . Sans la lecture volatile, la lecture de
instance code> dans l'instruction de retour pourrait soulever avant la lecture de
initialisée code> comme ceci. P>
class Singleton
{
private static object slock = new object();
private static Singleton instance;
private static int initialized;
private Singleton() {}
public Instance {
get {
var local = instance;
if (initialized == 0) {
lock (slock) {
if (initialized == 0) {
instance = new Singleton();
initialized = 1;
}
}
}
return local;
}
}
}
Merci d'avoir critiqué le titre. En effet, je ne voulais pas dire que Joe proposait cela comme une technique de verrouillage double vérifiée générale, mais uniquement à la situation et à la plate-forme spécifiques qu'il a décrites. J'aurais pu mieux reformuler le titre.
@Ryaner: Oui, je n'ai jamais pensé un instant que vous avez impliqué que l'auteur préconisait cette variation. Il était évident de votre question que vous êtes bien informé de toutes les instructions de réorganisation Naunces. Je voulais juste fournir un certain contexte comment j'allais répondre à votre question.
Veuillez poster un lien vers quelque chose sur les "dangers" de verrouillage à double coffre. Le seul danger que je connaisse consiste à ne pas la mettre en œuvre correctement.
En outre, quelle version de .NET utilisez-vous? Si vous utilisez .NET 4.0, vous pouvez utiliser
paresseux code> pour l'initialisation paresseuse.