Problem z szablonem klas

0

Zadeklarowałem sobie klasę Wektor oraz klasę UkladRownanLiniowych, której składowymi są obiekty klasy Wektor. Jak widać chcę wybrać za Typ double ( definicje obiektów wew klasy UkladRownanLiniowych).
W funkcji main tworzę sobie obiekt klasy UkladRownanLiniowych i teraz chciałbym wywoływać kolejne funkcje. Przy każdym takim wywołaniu otrzymuję błędy od kompilatora :
Dla ( cin>>A ) :

//main.cpp:(.text+0x34): undefined reference to `std::basic_istream<char, std::char_traits<char> >& operator>><double>(std::basic_istream<char, std::char_traits<char> >&, Macierz<double>&)'

//
**

Po usunięciu klasy UkladRownanLiniowych , czyli dla samej klasy Wektor otrzymuje ten sam problem ..
Jeśli chodzi o deklaracje wszystko jest w dobrej kolejności, bo bez szablonów ten sam program działa**

template <typename Typ>
class Wektor {
        public: 
  Typ wek[10];
};
 
// Tworzę jakieś obiekty 
 
Wektor<double> V;
Wektor<double> blad;
Wektor<double> X;
 
// w definicji kazdej funkcji ktorej argumentami są obiekty klasy Wektor dokonuję takich operacji : 
 
template <typename Typ>
std::istream & operator >> (std::istream & StrmWe,  Wektor<Typ> & Wek){
if (!Wczytaj_OkreslonyZnak(StrmWe,"(" )) return StrmWe;
if(!Wczytaj_N_1_Par_Liczba_OkreslonyZnak(StrmWe,Wek)) return StrmWe;
Wczytaj_Liczbe_OkreslonyZnak(StrmWe,Wek[ROZMIAR-1],")");
return StrmWe;
}

}
// wywołanie w programie jakiejs funkcji , powiedzmy wew main() :

cin>>V;

1

Oczywiście wiesz, że definicje szablonów muszą być umieszczone w plikach tak, aby kod był dostępny podczas kompilacji wszystkiego, co ich używa?

Prosto mówiąc - gdzie masz definicję tego operatora? Powinna być w jednym z plików nagłówkowych a nie źródłowych.

0

Rozwiązałem to tak, że w plikach .cpp mam definicje funkcji szablonowych, natomiast w odpowiadających im plikach .hh mam szablon klasy. Chciałbym teraz połączyć to w taki sposób, żeby na końcu każdego pliku.hh dodać dyrektywę :

// szablon klasy ... 
#include "plik.cpp"
#endif

Wiem, że mógłbym po prostu wrzucić zawartość pliku .cpp ręcznie, ale mam dużo funkcji, chcę mieć porządek. Pojawił się jednak taki problem :
fatal error: plik.cpp: Nie ma takiego pliku ani katalogu
compilation terminated.

Katalogi mam w taki sposób :
prog/src/plik.cpp
prog/inc/plik.hh

Czyli chodzi o to, że plik .cpp jest w innym katalogu ? Dziwne, ze w drugą stronę to działa, gdy załączam .hh do pliku .cpp . Jaką mam dać komendę aby załączyć ten plik ?

1
  1. Za pomocą include dołączaj pliki: h,hpp,hh
  2. Klasy szablonowe mają być w całości w plikach: h,hpp,hh
    Z każdym innym podejściem na razie nie dasz rady, a jak już będziesz na odpowiednim poziomie aby dać sobie z tym rady to i tak nie będziesz tego robić bo to bez sensu.
0

Powiedzmy że chcę wygenerować klasę i funkcję dla typu double:

 // na początku programu :

Nazwa_Klasy<double> uklad;

Gdy ręcznie wstawię coś takiego, albo nazwę innego z typów własnych zamiast double, np Symbol ( mój typ wyliczeniowy) , oczywiście działa.
Chciałbym jednak , aby program wczytał sam pierwszy argument a później dokonał odpowiedniej definicji :
Powiedzmy tak :

 
char znak;
cin>>znak;

if(strchr("eabcd",rodzaj)) 
Nazwa_Klasy<Symbol> uklad;
else 
Nazwa_Klasy<double> uklad;

wynik :
src/main.cpp30: warning: unused variable ‘uklad’ [-Wunused-variable]
src/main.cpp39: warning: unused variable ‘uklad’ [-Wunused-variable]

src/main.cpp6: error: ‘uklad’ was not declared in this scope
make: *** [obj/main.o] Błąd 1

Triki typu string rodzaj ("double") w tych if'ach a potem Nazwa_Klasy<rodzaj>uklad; tez nie działają, czy istnieje jakiś sposób na to ?

0

Błąd jest pewnie dalej, gdzie używasz ten uklad.
Dokładnie to samo otrzymasz w przypadku:

if(true) int X; else double X;
X=3.5; // tu już nie istnieje żaden z powyższych X'ów

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