2017-08-10 1 views
1

Pourquoi j'obtiens un message d'erreur (erreur: appel de myCout() surchargé est ambigu) lorsque j'utilise deux espaces de noms différents dans la même fonction en utilisant la directive using namespace sans espace de nom complet?Utiliser un espace de noms différent dans la même fonction

#include <iostream> 
using namespace std; 

namespace first 
{ 
    void myCout(void) 
    { 
     cout<<"Hello World is great\n"; 
    } 
} 

namespace second 
{ 
    void myCout(void) 
    { 
     cout<<"Hello Sky is high\n"; 
    } 
} 

    int main(void) 
    { 

     cout<<"Hello World\n"; 
     using namespace first; 
      myCout(); 

     using namespace second; 
      myCout(); 

     return(0); 
    } 

Si je namespaces qualifiés pour myCout() dans le deuxième espace de noms comme indiqué ci-dessous, il n'y a pas de problème

int main(void) 
{ 
    cout<<"Hello World\n"; 
    using namespace first; 
    myCout(); 
    second::myCout(); 
    return(0); 
} 
+0

Une fois que vous ne 'en utilisant deuxième espace de noms,', il y a 2 définitions de 'myCout', la même signature, dans le cadre de 'main', donc - l'appel est ambigu. –

Répondre

5

using directives respectent la portée. Ainsi, vous pouvez introduire un nouveau champ de bloc pour limiter la disponibilité des symboles introduits par chacun:

int main(void) 
{ 
    cout<<"Hello World\n"; 
    { 
     using namespace first; 
     myCout(); 
    } 

    { 
     using namespace second; 
     myCout(); 
    } 

    return(0); 
} 

Normalement, et de manière à éviter les conflits et l'imbrication profonde, essayez de tirer en seulement les identifiants dont vous avez besoin avec un using déclaration à la place. Si, par exemple, vous ne avez toujours voulu utiliser la classe foo de first alors il n'y aurait pas d'ambiguïté à ce qui suit:

using first::foo; 
using namespace second; 
3

using namespace ... directives ne créent pas un chemin ordonné; ils ne remplacent pas tous les précédents. Donc, oui, votre code crée une situation ambiguë.

1

D'abord vous utilisez namespace first, ainsi le myCout du premier espace de noms est introduit. Ensuite, vous utilisez namespace second, provoquant l'entrée en jeu de l'autre myCout. Le deuxième espace de noms ne remplace pas l'espace de noms précédent. Par conséquent, lorsque vous appelez myCout pour la deuxième fois, deux définitions sont en jeu, ce qui oblige le compilateur à le considérer comme un appel ambigu.

En d'autres termes:

int main(void) 
{ 
    using namespace first; // `myCout` of the 1st namespace is introduced 
    myCout(); 

    using namespace second; // `myCout` of the 2nd namespace is introduced 
    // and does not override the first namespace! 

    myCout();    // Which `myCout`? Of the first or second? 

    return 0; 
}