2011-01-12 12 views
9

Używam prywatnego dziedziczenia w projekcie, w "zaimplementowanym w kategoriach" -sense. Klasa bazowa definiuje operator [] i jest to funkcja, której chcę użyć. W ten sposób mam jednak Prywatne dziedziczenie za pomocą dyrektywy, przeciążenia?

class A : private B { 
    using B::operator[]; 
    // ... 
}; 
Jak jednak mogę kontrolować, która wersja operatora [] otrzymuję? W rzeczywistości potrzebuję więcej niż jednej, zarówno wersji const, jak i non- const. Czy można to osiągnąć?

+3

W takim przypadku można użyć kompozycji, aby uzyskać pożądany wynik, a nie prywatne dziedziczenie. – James

+1

Tak, wiem ... Zmieniłem go na prywatne dziedziczenie, aby zmniejszyć ilość kodu przekierowania. Więc to nie jest możliwe? W jaki sposób funkcja jest wybierana? – carlpett

+0

Twój kod będzie znacznie łatwiejszy do napisania i konserwacji, jeśli użyjesz tutaj kompozycji zamiast prywatnego dziedziczenia. Zasadą jest, aby nie używać funkcji C++, gdy nie są one absolutnie konieczne (z tego, co powiedziałeś do tej pory, prywatne dziedziczenie nie jest w tym przypadku konieczne). –

Odpowiedz

6

Rozumiem, że Twój using powinien automatycznie powodować wszystkie przeciążenia operatora. Czy są jakieś przeciążenia, które chcesz wykluczyć z przeniesienia do klasy dziecka? W takim przypadku lepiej podzielić pracę na kilka inaczej nazwanych funkcji w rodzica i tylko te, których potrzebujesz.

+0

Też tak bym pomyślał, ale dostaję błędy kompilacji od const-discarding, pomimo tego, że istnieją wersje zwracające zarówno "T &", jak i "const T &" (szablon o nazwie T) – carlpett

+0

To jest jeden z nich "magicznie naprawiony "Czasy ... Po przejrzeniu kodu i ponownym skompilowaniu, nagle działa, a ja nie mogę dla życia zrozumieć, co zmieniłem. Zmieniło się jednak to, że dowiedziałem się trochę więcej o dziedziczeniu, więc dzięki! – carlpett

2

to robi zgodnie z oczekiwaniami:

class A 
{ 
public: 
    int operator[](int idx) { return 0; } 
    int operator[](int idx) const { return 1; } 
}; 

class B : public A 
{ 
public: 
    using A::operator[]; 

    void opa() { cout << operator[](1) << endl; } 
    void opb() const { cout << operator[](1) << endl; } 
}; 

int main(void) 
{ 
    B b; 
    b.opa(); 
    b.opb(); 

    const B d = B(); 
    cout << d[1] << endl; // should trigger the const version of operator[] 
    return 0; 
} 

Innymi słowy, odpowiednie const/Wersje non const są wstrzykiwane do B. UWAGA: Jeśli wersja const nie zostanie podana, otrzymasz błąd kompilatora (działa to, czy dziedziczenie jest prywatne czy publiczne).

+0

Dzięki, dobry przykład! – carlpett

+0

Dodałbym również "b [2];" lub podobny do 'main', aby pokazać, że funkcje operatora mogą być używane bezpośrednio z zewnątrz' klasy B'. – aschepler

+0

@aschepler, dobry punkt, zaktualizuje ... – Nim

Powiązane problemy