I decided to make a linked list program using classes and templates.
I implemented my linked list and added some basic functions, everything worked just fine. Then I proceeded to add templates...
First, the error list:
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: void __thiscall List<int>::addNode(int)" (?addNode@?$List@H@@QAEXH@Z) referenced in function _main
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: void __thiscall List<int>::removeAll(void)" (?removeAll@?$List@H@@QAEXXZ) referenced in function _main
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: int __thiscall List<int>::length(void)" (?length@?$List@H@@QAEHXZ) referenced in function _main
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: void __thiscall List<int>::displayList(void)" (?displayList@?$List@H@@QAEXXZ) referenced in function _main
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: class Node<int> & __thiscall List<int>::getNodeAt(int)" (?getNodeAt@?$List@H@@QAEAAV?$Node@H@@H@Z) referenced in function "public: class Node<int> & __thiscall List<int>::operator[](int const &)" (??A?$List@H@@QAEAAV?$Node@H@@ABH@Z)
1>Advanced Linked Lists.obj : error LNK2019: unresolved external symbol "public: void __thiscall List<int>::moveNode(int,int)" (?moveNode@?$List@H@@QAEXHH@Z) referenced in function _main
1>C:\Users\...\Console\Advanced Linked Lists\Debug\Advanced Linked Lists.exe : fatal error LNK1120: 6 unresolved externals
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========
I have no idea what is going on with my program.
All I know is that something is wrong with the templates in "List.cpp", because everything worked before I added them to that file.
Following: Node.h
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
#pragma once
template<class T>
class Node
{
private:
Node* next;
T data;
public:
Node(int val) :data(val), next(0){}
Node() :data(0), next(0){}
int getData(){ return data; }
void setData(T value){ data = value; }
Node* getNext(){ return next; }
void setNext(Node* node){ next = node; }
~Node(){ /* No need */ }
};
Ok, first about waht include does: it just copy-pastes everything from header file to the place where include is.
Second: about separate compilation.
Only cpp fileas are compiled, and each compiled file has no slightest idea about other files which are probably compiled too. If compiler finds used function/class definition in current cpp file, it uses it.
If it can not find definition, but finds a declaration (a promise that this finction/class will be defined in other files) it leaves a note to the linker to find that in another files during linkng.
And finally on templates.
Templates are not magic thing accepting all types. It is as name suggests: a template for generating different function/classes. It tells compiler: "if you want an instance with type T = int, copy that template and replace all T's with int". That means if you use templated function with int and then double, compiler will generate two functions: one for int and one for double.
That also means that if function/class is not used, it won't be generated. You never use .erase() method in vector? Code for it will never be actually generated.
When you have bunch of templates in cpp file and no code using them in that file, nothing is generated.
But. In your header file you have a class definition. Which you use. And inside it you have member function declarations. And you use them. You use promises that they would be found elsewhere. But file actually containing templates for definition does not know what needs to be created and if it needs created at all. So linker searches for function definitions, does not finds them and gives you an error.
If you look into standard headers, you will find out that any templated class is fully defined inside that header.