Domanda

Perché se abbiamo puro operatore di assegnazione virtuale in una classe base, poi abbiamo attuare tale operatore sulla classe derivata, dare errore di linker sulla classe di base?

Al momento ho solo la seguente spiegazione su http://support.microsoft.com/kb/130486 , ha detto che il comportamento è di progettazione in quanto le normali regole di ereditarietà non si applica .

non è chiaro per me, perché è generare errore di linker in base alla progettazione? Qualcuno può darmi spiegazione più chiara su questo?

edit: aggiunto il codice semplificato , di cui è verificato l'errore:

class __declspec(dllexport) BaseClass {
public:
    int memberA;
    virtual BaseClass& operator=(const BaseClass& rhs) = 0;
};

class __declspec(dllexport) DerivedClass : public BaseClass {
public:
    int memberB;
    DerivedClass():memberB(0) {}
    virtual BaseClass& operator=(const BaseClass& rhs) {
        this->memberA = rhs.memberA;
        this->memberB = 1;
        return *this;
    }
};

int main(void)
{
    DerivedClass d1;
    DerivedClass d2;

    BaseClass* bd1 = &d1;
    BaseClass* bd2 = &d2;

    *bd1 = *bd2;
}

il codice verrà compilato senza errori senza __declspec(dllexport) e / o senza operatore virtuale pura = dichiarazione sulla classe di base.

senza __declspec(dllexport) dopo l'assegnazione di *bd1 = *bd2;, d1 :: memberB è 1, ma con __declspec(dllexport) d1 :: memberB rimane invariato

con __declspec(dllexport), e senza dichiarazione virtuale pura, dopo l'assegnazione di *bd1 = *bd2;, d1 :: memberB rimane invariato

È stato utile?

Soluzione

Dalla sezione 12.8 dello standard:

13 L'operatore di assegnazione copia implicitamente definito per l'assegnazione di classe X esegue membro a membro dei suoi oggetti secondari. Il classi base dirette di X vengono assegnati prima, in ordine di loro dichiarazione nella base-specificatore-list , e quindi l'immediato membri di dati non statici della X sono assegnati, nell'ordine in cui sono stati dichiarati nella definizione della classe. ogni sotto-oggetto è assegnato in modo appropriato per il tipo:

- se il sotto-oggetto è di tipo di classe, si utilizza l'operatore di assegnazione copia per classe (come per la qualificazione esplicita; cioè, ignorando eventuali funzioni imperativi virtuali in classi derivate più);

La sottoclasse è utilizzando la copia operatore di assegnazione implicitamente definito, e non esiste una definizione di operatore di assegnamento copia della classe base, ma si è dichiarato, in modo da ottenere un errore di collegamento al posto di un errore di compilazione.

Altri suggerimenti

operatore = non viene ereditata. Il tuo codice è privo di significato in C ++, in modo da compilatori sono liberi di rilasciare qualsiasi errore che vogliono per esso.

Dall'articolo KB si indicò: http://support.microsoft.com/kb/130486

  

Da operatore = non è ereditata, ogni dichiarazione dell'operatore = nella classe di base è inutilizzato e inutile. Non dichiarare l'operatore = nella classe base.

E 'probabilmente solo un effetto collaterale di come si compilano, e sono solo farti sapere che non lo considerano un problema, quindi non c'è alcuna necessità di risolvere il problema. "In base alla progettazione" non significa necessariamente che essi specificamente deciso che questo errore linker è il messaggio di errore diritto di dare per questa situazione - il codice è sbagliato, si ottiene un errore, quindi dal loro punto di vista - sono fatto.

Nel codice di esempio:

class A
{
public :
   // To workaround LNK2001, comment the following line.
   virtual const A& operator=( const A& f ) = 0;
};

class B : public A
{
public :
   const A& operator=( const A& g ) {return g;}
};

B aB1, aB2;

int /*void*/ main( void )
{
   aB2 = aB1;
}

linea aB2 = aB1 non mette const A& B::operator=(const A&), ma richiede invece la B& operator=(const B&); fornito automaticamente che a sua volta utilizza l'operatore di assegnazione per assegnare la parte di base della classe. Ma quando si tratta di collegamento, si scopre che che è stato mai attuato.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top