Maison >développement back-end >C++ >Pourquoi l'instanciation de modèle en deux phases de MSVC s'écarte-t-elle de la norme C ?

Pourquoi l'instanciation de modèle en deux phases de MSVC s'écarte-t-elle de la norme C ?

Linda Hamilton
Linda Hamiltonoriginal
2024-12-24 14:06:15185parcourir

Why Does MSVC's Two-Phase Template Instantiation Deviate from the C   Standard?

Instanciation de modèle en deux phases dans Microsoft Visual C : quel est le problème ?

Microsoft Visual C (MSVC) a été critiqué pour son prétendu implémentation incorrecte de l'instanciation de modèle en deux phases. Cette méthodologie, telle que définie par la norme C, se compose de deux phases distinctes :

Première phase :

  • Effectue la syntaxe de base et la vérification de type.
  • Ne vérifie pas la déclaration ou l'existence de noms non dépendants utilisés dans modèles.

Deuxième phase :

  • Résout et lie les noms non dépendants à leurs déclarations.
  • Étend la recherche d'espace de noms pour les noms dépendants avec des déclarations accumulées depuis le premier phase.

Déficiences de MSVC :

Le principal problème de MSVC réside dans son incapacité à effectuer une recherche précoce (première phase) pour les expressions non dépendantes. Au lieu de cela, il reporte toutes les recherches jusqu'à la deuxième phase, ce qui entraîne un comportement incorrect. De plus, la deuxième phase de MSVC ne respecte pas correctement la spécification pour la recherche non-ADL, qui ne doit pas être étendue au cours de cette phase.

Exemple :

Considérez le code suivant :

int foo(void*);

template<typename T> struct S {
  S() { int i = foo(0); }
};

void foo(int);

int main() {
  S<int> s;
}

Un compilateur conforme aux normes doit lier l'appel 'foo(0)' à 'foo(void*)' pendant la première phase. Cependant, MSVC le lie de manière incorrecte à 'foo(int)' au cours de la deuxième phase, ce qui entraîne une erreur lors de l'initialisation.

Couche supplémentaire d'inexactitude :

Même pendant Lors de la deuxième phase, MSVC ne respecte pas la stipulation de la norme selon laquelle la recherche non-ADL ne doit pas être étendue. Cela se traduit par l'inclusion de déclarations qui n'étaient pas disponibles lors de la première phase, entraînant un comportement inattendu.

Exemple :

namespace N {
  struct S {};
}

void bar(void *) {}

template <typename T> void foo(T *t) {
  bar(t);
}

void bar(N::S *s) {}

int main() {
  N::S s;
  foo(&s);
}

Ici, 'bar(t )' devrait se résoudre en 'void bar(void ),' bien qu'il ait été résolu au cours de la deuxième phase. Pourtant, MSVC le résout de manière incorrecte en « barre vide (N::S s) », démontrant sa mise en œuvre défectueuse.

Conclusion :

Les deux- L'implémentation de l'instanciation du modèle de phase ne parvient pas à adhérer pleinement à la norme C, ce qui entraîne un comportement incorrect lorsqu'il s'agit à la fois d'expressions non dépendantes et de recherche non ADL. Ces déficiences peuvent entraîner des erreurs inattendues au moment de la compilation et un comportement du programme.

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!

Déclaration:
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