Klasa abstrakcyjna a tworzenie jej pochodnego obiektu

2014-11-04 21:24
Brakl
0

Cześć. Wie ktoś może, jak poradzić sobie z takim problemem. Otóż, mam klasę abstrakcyjną. Ma ona 2 dzieci.
Chciałbym przechowywać w kontenerze wskaźniki na "rodzeństwo". Chciałbym w metodzie nowej klasy, móc kopiować, już istniejący konterner jednak nie moge tego zrobić w ten sposób bo Klasa Sklep, mająca dzieci warzywaniak, market, jest abstrakcyjna.

Vector.push_back(new Sklep(*member));  

gdzie member jest wskaźnikiem na kopiowaną podklasę.

Pozostało 580 znaków

2014-11-04 21:27
0

Niech obiekt sam umie sie sklonować.


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...

Pozostało 580 znaków

2014-11-04 21:32
Brakl
0

Sklep?

edytowany 1x, ostatnio: furious programming, 2016-12-13 18:26

Pozostało 580 znaków

2014-11-04 21:35
1

Nie, "rodzeństwo"


Wykonuję programy na zamówienie, pisać na Priv.
Asm/C/C++/Pascal/Delphi/Java/C#/PHP/JS oraz inne języki.

Pozostało 580 znaków

2014-11-04 21:58
Brakl
0

A o co chodzi z tym klonowaniem, gdzie mogę znaleść informacje nt. temat?

edytowany 1x, ostatnio: furious programming, 2016-12-13 18:26

Pozostało 580 znaków

2014-11-04 22:03
0

Niech klasa Sklep ma metodę abstrakcyjną clone() zwracającą Sklep* i niech jej podklasy ją implementują poprzez utworzenie nowego obiektu i skopiowanie się do niego. Czyli dla podklas to będzie coś w stylu

virtual Sklep* clone(){
  return new Warzywniak(this);
}

Zakładając że masz tam konstruktor kopiujący w tej klasie.


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...
@n0name_l nie chciało mi sie sprawdzać czy C++ ma kowariantne typy zwracane. Java, w której mocniej siedzę aktualnie, nie ma. Tam tylko typy metod są kontrawariantne (możesz w klasie pochodnej mieć argumenty metod bardziej ogólne niż w klasie bazowej) ale typy zwracane są inwariantne i nie można w klasie pochodnej ustawić typu zwracanego na bardziej szczegółowy. - Shalom 2014-11-04 23:12

Pozostało 580 znaków

2014-11-04 22:30
Brakl
0

Dzięki ziomek, o to chodziło!! Korzystając z okazji chcaiłbym zadać Ci jeszcze jedno pytanie, bo tą funkcją wirtulana, rozwiązałeś u mnie kilka innych problemów. Dlaczego takie coś działa

 void Register::Add(Sklep *newone) {
    Vector.push_back(newone->clone());
}

A takie coś, powoduję już błędy w pamieci, gdy przechodze Vector, a niby to samo.

 void Register::Add(Sklep *newone) {
    Vector.push_back(new Sklep(*newone));
}

Czy z tego wynika, że klasa sklep nie potrafi prze konwertować się na podklase?

edytowany 1x, ostatnio: furious programming, 2016-12-13 18:26

Pozostało 580 znaków

2014-11-04 22:33
0

Ależ potrafi, tyle że piszesz new Sklep to co kompilator ma cię zignorować?


Wykonuję programy na zamówienie, pisać na Priv.
Asm/C/C++/Pascal/Delphi/Java/C#/PHP/JS oraz inne języki.

Pozostało 580 znaków

2014-11-04 22:43
Brakl
0

Nie rozumiem to co mam napisać? Nie mogę jawnie wywołać konstruktora podklasy?

edytowany 1x, ostatnio: furious programming, 2016-12-13 18:26

Pozostało 580 znaków

2014-11-04 22:45
0

@Brakl przecież to są dwie ZUPEŁNIE INNE RZECZY! Popatrz który konstruktor woła metoda clone(). Woła konstruktor klasy pochodnej a nie klasy bazowej!
Żeby zrobić coś takiego jak napisałeś to musiałbyś zrobić takie brzydkie coś:

 void Register::Add(Sklep *newone) {
    Warzywniak* wskaznik = dynamic_cast<Warzywniak*>(newone);
    if (wskaznik !=NULL){
        Vector.push_back(new Warzywniak(*newone));
    }else{
        Vector.push_back(new Market(*newone));  
    }
}

Korzystam tutaj z RTTI -> sprawdzam realny typ obiektu w trakcie wykonania programu i na tej podstawie wołam odpowiedni konstruktor. Ale sam widzisz że to słaba metoda. Jakbyś miał 100 podklas to byś miał 100 ifów ;] Wirtualna metoda clone() jest dużo lepsza.


Masz problem? Pisz na forum, nie do mnie. Nie masz problemów? Kup komputer...
edytowany 3x, ostatnio: Shalom, 2014-11-04 22:50
nullptr albo NULL. - Endrju 2014-11-04 22:49
Za dużo javy ostatnio ;) fixed - Shalom 2014-11-04 22:50
Trzeba dodać, że chce utworzyć obiekt klasy abstrakcyjnej. - Sarrus 2014-11-04 22:50

Pozostało 580 znaków

2014-11-04 22:49
Brakl
0
Shalom napisał(a):

@Brakl przecież to są dwie ZUPEŁNIE INNE RZECZY! Popatrz który konstruktor woła metoda clone(). Woła konstruktor klasy pochodnej a nie klasy bazowej!
Żeby zrobić coś takiego jak napisałeś to musiałbyś zrobić takie brzydkie coś:

void Register::Add(Sklep *newone) {
Warzywniak* wskaznik = dynamic_cast<Warzywniak*>(newone);
if (wskaznik !=null){
Vector.push_back(new Warzywniak(*newone));
}else{
Vector.push_back(new Market(*newone));  
}
}

No rozumie, ale pisząc

  void Register::Add(Sklep *newone) {
    Vector.push_back(new Warzywniak(*newone));
}

Zamkne sobie droge zeby stworzyc, market. Czyli metoda z clonem jest jedyna mozliwa?

Pozostało 580 znaków

Liczba odpowiedzi na stronę

1 użytkowników online, w tym zalogowanych: 0, gości: 1, botów: 0