Wątek przeniesiony 2017-11-08 13:40 z C/C++ przez kq.

Vector na różne obiekty

0

Witam, potrzebuję zrobić vector z wskaźnikami klasy bazowej na wskaźniki klas pochodnych.
Dodam, że jeśli wywołam w mainie tak:

static vector<Roslina*>wektor;
wektor.push_back(new Kwiatek(roc,wie,kol,lp));

...
to wszystko się kompiluje, problem pojawia się jeśli chcę to wrzucić w klasę:

class Kontener {
    static vector<Roslina*>wektor;
    public:
    static void Dodaj(bool roc, int wie, string kol, int lp);
   // static void wyswietl_calosc();
};

void Kontener::Dodaj(bool roc, int wie, string kol, int lp) {

    wektor.push_back(new Kwiatek(roc,wie,kol,lp));
}

kompilacja takiego przypadku daje:
|undefined reference to `Kontener::wektor'|
||error: ld returned 1 exit status|

1

To nie ma się nijak do wektora, po prostu musisz w jednym TU (plik cpp) zdefiniować ten element:

vector<Roslina*> Kontener::wektor;

Przy czym nie używaj nagich wskaźników w taki sposób, tutaj właśnie powinieneś użyć unique_ptr.

0

Rozumiem, że po unique_ptr pamięć jest zwalniana automatycznie.
W jaki sposób mogę skorzystać z unique_ptr.

1
vector<unique_ptr<foo>> foos;

Dodajesz za pomocą emplace_back lub push_back, zależnie od tego jakiego typu obiekt dodajesz.

Oczywiście foo musi mieć wirtualny destruktor.

1
class Kontener {
    static vector<unique_ptr<Roslina>>wektor;
public:
    static void Dodaj(bool roc, int wie, string kol, int lp);
   // static void wyswietl_calosc();
};

vector<unique_ptr<Roslina>> Kontener::wektor;

void Kontener::Dodaj(bool roc, int wie, string kol, int lp) {
    wektor.emplace_back(new Kwiatek(roc,wie,kol,lp));
}

Swoją drogą to używanie pól statycznych w takim kontekście to bardzo zły pomysł.

0

Zrobiłem tak jak pisał MarekR22, niestety dostałem błędy podczas kompilacji. Dlaczego to bardzo zły pomysł, chciałem aby ta klasa była abstrakcyjna.
Błąd:
screenshot-20171108160328.png

0

Jak się ma pole statyczne do abstrakcyjności klasy? To dla mnie jakaś (heh, heh) abstrakcja ;​)

Możliwe, że brakuje ci std::, lub #include <memory>

0

Używam using namespace std, a bibliotekę memory mam dołączoną.

0

No to pokaż kod.

0
#include <iostream>
#include <cstdio>
#include <vector>
#include <memory>

using namespace std;

////////////////////////////////////////////////////////////////////////////

class Roslina {
protected:
    const static int DLUGOSC=7 ;
    char Nazwa[DLUGOSC];
    bool Roczna;
    int Wiek;
public:
    Roslina(bool = false, int =0);
    ~Roslina(){};
    virtual void wypisz();
};

Roslina::Roslina(bool roc, int wie) {
    int i;
    for (i=0;i<DLUGOSC-1;i++) {
        Nazwa[i]='x';
    }
    Nazwa[i+1] = '/0';
    Roczna = roc;
    Wiek = wie;
}

void Roslina::wypisz(){
    cout << "Nazwa: " ;
    for (int i=0;i<DLUGOSC-1;i++) cout << Nazwa[i] ;
    cout << endl << "Roslina: " ;
    if (Roczna == 0 ) cout << "jednoroczna" << endl ;
    else cout << "wieloroczna" << endl ;
    cout << "Wiek: " << Wiek << endl ;
}

////////////////////////////////////////////////////////////////////////////

class Kwiatek:public Roslina {
protected:
    string Kolor;
    int Liczba_platkow;
public:
    Kwiatek(bool = false, int=0, string="brak", int=0) ;
    ~Kwiatek(){};
    Kwiatek(const Kwiatek&);
    virtual void wypisz();
    Kwiatek& operator=(Kwiatek&);
};

Kwiatek::Kwiatek(bool roc, int wie, string naz, int licz_pl):Roslina(roc,wie) {
    Kolor = naz;
    Liczba_platkow = licz_pl;
}

Kwiatek::Kwiatek(const Kwiatek& k) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = k.Nazwa[i] ;
    }
    Roczna = k.Roczna;
    Wiek = k.Wiek;
    Kolor = k.Kolor;
    Liczba_platkow = k.Liczba_platkow;
}

void Kwiatek::wypisz() {
    Roslina::wypisz();
    cout << "Kolor: " << Kolor << endl;
    cout << "Ilosc platkow: " << Liczba_platkow << endl << endl;
}

Kwiatek& Kwiatek::operator=(Kwiatek& k) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = k.Nazwa[i] ;
    }
    Roczna = k.Roczna;
    Wiek = k.Wiek;
    Kolor = k.Kolor;
    Liczba_platkow = k.Liczba_platkow;
}

////////////////////////////////////////////////////////////////////////////

class Drzewo:public Roslina {
protected:
    int Liczba_lisci;
    int Liczba_galezi;
public:
    Drzewo(bool = false, int=0, int=0, int=0);
    ~Drzewo(){};
    Drzewo (const Drzewo&);
    virtual void wypisz();
    Drzewo& operator=(Drzewo&);
};

Drzewo::Drzewo(bool roc, int wie, int ill, int ilg):Roslina(roc,wie){
    Liczba_galezi = ilg;
    Liczba_lisci = ill;
}

Drzewo::Drzewo(const Drzewo& d) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = d.Nazwa[i] ;
    }
    Roczna = d.Roczna;
    Wiek = d.Wiek;
    Liczba_galezi = d.Liczba_galezi;
    Liczba_lisci = d.Liczba_lisci;
}

Drzewo& Drzewo::operator=(Drzewo& d) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = d.Nazwa[i] ;
    }
    Roczna = d.Roczna;
    Wiek = d.Wiek;
    Liczba_galezi = d.Liczba_galezi;
    Liczba_lisci = d.Liczba_lisci;
}

void Drzewo::wypisz() {
    Roslina::wypisz();
    cout << "Ilosc lisci: " << Liczba_lisci << endl;
    cout << "Ilosc galezi: " << Liczba_galezi << endl << endl;
}

////////////////////////////////////////////////////////////////////////////

class Owadozerca:public Roslina {
protected:
    string Pokarm;
public:
    Owadozerca(bool = false, int=0, string = "nic nie jada");
    ~Owadozerca(){};
    Owadozerca (const Owadozerca&);
    virtual void wypisz();
    Owadozerca& operator=(Owadozerca&);
};

Owadozerca::Owadozerca(bool roc, int wie, string pok):Roslina(roc,wie) {
    Pokarm = pok;
}

Owadozerca::Owadozerca(const Owadozerca& o) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = o.Nazwa[i] ;
    }
    Roczna = o.Roczna;
    Wiek = o.Wiek;
    Pokarm = o.Pokarm;
}

Owadozerca& Owadozerca::operator=(Owadozerca& o) {
    int i;
    for (i=0;i<DLUGOSC;i++) {
        Nazwa[i] = o.Nazwa[i] ;
    }
    Roczna = o.Roczna;
    Wiek = o.Wiek;
    Pokarm = o.Pokarm;
}

void Owadozerca::wypisz() {
    Roslina::wypisz();
    cout << "Co je: " << Pokarm << endl << endl;
}

////////////////////////////////////////////////////////////////////////////

class Kontener {
    static vector<unique_ptr<Roslina>>wektor;
public:
    static void Dodaj(bool roc, int wie, string kol, int lp);
   // static void wyswietl_calosc();
};

vector<unique_ptr<Roslina>> Kontener::wektor;

void Kontener::Dodaj(bool roc, int wie, string kol, int lp) {
    wektor.emplace_back(new Kwiatek(roc,wie,kol,lp));
}

////////////////////////////////////////////////////////////////////////////

int main()
{
Roslina* wsk;
Kwiatek kw;
Drzewo drz;
Owadozerca owa;


wsk = &kw;
wsk->wypisz();
wsk = &drz;
wsk->wypisz();
wsk = &owa;
wsk->wypisz();

return 0;
}

1

Jaki masz kompilator/IDE? "U mnie działa", więc pewnie nie masz trybu C++11/14/17 włączonego.

1

zapewne gdzieś brakuje przełącznika -std=c++11

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