2015-07-13 4 views
19

ho il seguente codice:g ++ errore di compilazione "... è protetto da in questo contesto", mentre non c'è nessun errore con clang

#include <iostream> 

class BaseClass { 
protected: 
static int x; 
}; 

int BaseClass::x; 

class DerivedA: public BaseClass { 
public: 
    DerivedA() { 
     x = 3; 
    } 
};  

class DerivedB: public BaseClass { 
public: 
    DerivedB() { 
     std::cout << DerivedA::x; 
    } 
}; 

int main(int argc, char* argv[]) { 
     DerivedB b; 
} 

Compilare con g ++ (g++ classtest.cpp) ricevo il seguente errore:

classtest.cpp: In constructor ‘DerivedB::DerivedB()’:
classtest.cpp:9:5: error: ‘int BaseClass::x’ is protected
int BaseClass::x;
^ classtest.cpp:25:32: error: within this context
std::cout << DerivedA::x;

Quando compilo con clang ++ (clang++ classtest.cpp) non ci sono errori.

Perché g ++ restituisce l'errore di compilazione?

Io uso g ++ versione 5.1.0 e clang ++ versione 3.6.1

+4

Compilare anche in MVS2015 – Zereges

+1

Sono più sorpreso del fatto che il clang ** non sia ** lanciando un errore ... Ma posso confermare, non lo è. –

+2

@DrewDormann Perché? Sono sorpreso dall'errore: nonostante 'DerivedA ::', in realtà accede a un membro protetto di 'BaseClass', da una classe derivata da' BaseClass'. – hvd

risposta

17

GCC bug. [Class.access.base]/p5:

A member m is accessible at the point R when named in class N if

  • m as a member of N is public, or
  • m as a member of N is private, and R occurs in a member or friend of class N , or
  • m as a member of N is protected, and R occurs in a member or friend of class N , or in a member of a class P derived from N , where m as a member of P is public, private, or protected, or
  • there exists a base class B of N that is accessible at R , and m is accessible at R when named in class B .

N è DerivedA, m è x, R è il costruttore di DerivedB. Esiste una classe base BaseClass di DerivedA che è accessibile a R e x chiamato in classe BaseClass (cioè, BaseClass::x) è chiaramente accessibile a R, quindi dal quarto punto, DerivedA::x è accessibile a R.

+1

Questo è un bug helluva. Anche se il proiettile in questione non è il più comune, non è oscuro in alcun modo. –

+6

Non riesci a trovarlo su gcc's bugzilla - vuoi inviare? – Barry

+3

Grazie per la chiara spiegazione. Peccato che non possiamo offrire ricompense per le attività, come aprire una segnalazione di bug :) – Dreamcooled