This question already has answers here:
Why can templates only be implemented in the header file?
(17 answers)
Closed 5 years ago.
i'm just writing an array class as practice in Microsoft Visual Studio 2010 but i'm getting some annoying errors. here they are:
1>test.obj : error LNK2019: unresolved external symbol "public: __thiscall arrays<int>::~arrays<int>(void)" (??1?$arrays#H##QAE#XZ) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: int & __thiscall arrays<int>::operator[](int)" (??A?$arrays#H##QAEAAHH#Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: bool __thiscall arrays<int>::operator==(class arrays<int> const &)const " (??8?$arrays#H##QBE_NABV0##Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: int const & __thiscall arrays<int>::operator=(class arrays<int> const &)" (??4?$arrays#H##QAEABHABV0##Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: __thiscall arrays<int>::arrays<int>(class arrays<int> const &)" (??0?$arrays#H##QAE#ABV0##Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "class std::basic_istream<char,struct std::char_traits<char> > & __cdecl operator>>(class std::basic_istream<char,struct std::char_traits<char> > &,class arrays<int> const &)" (??5#YAAAV?$basic_istream#DU?$char_traits#D#std###std##AAV01#ABV?$arrays#H###Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "class std::basic_ostream<char,struct std::char_traits<char> > & __cdecl operator<<(class std::basic_ostream<char,struct std::char_traits<char> > &,class arrays<int> const &)" (??6#YAAAV?$basic_ostream#DU?$char_traits#D#std###std##AAV01#ABV?$arrays#H###Z) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: int __thiscall arrays<int>::getsize(void)const " (?getsize#?$arrays#H##QBEHXZ) referenced in function _wmain
1>test.obj : error LNK2019: unresolved external symbol "public: __thiscall arrays<int>::arrays<int>(int)" (??0?$arrays#H##QAE#H#Z) referenced in function _wmain
1>c:\users\bm\documents\visual studio 2010\Projects\arrays\Debug\arrays.exe : fatal error LNK1120: 9 unresolved externals
how can I fix them?
here is my code:
arrays.h
#ifndef ARRAYS_H
#define ARRAYS_H
#include <iostream>
using namespace std;
template <typename T>
class arrays{
friend ostream &operator<<(ostream &output, const arrays &a);
friend istream &operator>>(istream &input, const arrays &a);
public:
arrays(int = 10);
arrays(const arrays &);
~arrays();
int getsize() const;
const T &operator=(const arrays &);
bool operator==(const arrays &) const;
bool operator!=(const arrays &right) const{
return !((*this)==right);
}
T &operator[](int);
T operator[](int) const;
private:
int size;
T *ptr;
};
#endif
arrays.cpp
#include "stdafx.h"
#include <iostream>
#include "arrays.h"
#include <cstdlib>
using namespace std;
template <typename T>
arrays<T>::arrays(int mysize){
size = mysize;
ptr = new(int[size]);
for(int i = 0; i< size; i++)
ptr[i] = 0;
}
template <typename T>
arrays<T>::arrays(const arrays<T> &myarray){
size = myarray.size;
ptr = new(int[size]);
for(int i = 0; i< size; i++){
ptr[i] = myarray.ptr[i];
}
}
template <typename T>
arrays<T>::~arrays(){
delete [] ptr;
}
template <typename T>
int arrays<T>::getsize() const {
return size;
}
template <typename T>
const T &arrays<T>::operator=(const arrays<T> &right){
if ( &right != this){
if(size != right.size){
delete [] ptr;
size= right.size;
ptr = new(int[size]);
}
for(int i =0; i < size; i++)
ptr[i] = right.ptr[i];
}
return *this;
}
template <typename T>
bool arrays<T>::operator==(const arrays<T> &right) const{
if(right.size != size)
return false;
for(int i = 0; i<size; i++)
if(ptr[i] != right.ptr[i])
return false;
return true;
}
template <typename T>
T &arrays<T>::operator[](int subscript) {
if(subscript < 0 || subscript >= size){
cout << "error: subscript out of range";
}
return ptr[subscript];
}
template <typename T>
T arrays<T>::operator[](int subscript) const {
if(subscript < 0 || subscript >= size){
cout << "error: subscript out of range";
exit(1);
}
return ptr[subscript];
}
template <typename T>
istream &operator>>(istream &input, const arrays<T> &a){
for(int i = 0; i< a.size; i++)
input >> a.ptr[i];
return input;
}
template <typename T>
ostream &operator<<(ostream &output, arrays<T> &a){
for(int i= 0; i<a.size;i++)
output << a.ptr[i];
return output;
}
any help would be appreciated.
Implementation code for a template class must live in the header, not in the .cpp file. This is required so that other code that use your template class can "instanciate" it's code based on the template parameter.
So just move all your code from your .cpp to your .h and you're good to go.
Related
#include <iostream>
class t1
{
public:
~t1();
static t1& fun();
private:
t1()
{
}
};
t1& t1::fun()
{
return t1();
}
int main()
{
t1::fun();
return 0;
}
I am getting unresolved external symbol. please help. the errors are below
Error 2 error LNK2019: unresolved external symbol "public: __thiscall t1::~t1(void)" (??1t1##QAE#XZ) referenced in function "public: static class t1 & __cdecl t1::fun(void)" (?fun#t1##SAAAV1#XZ) D:\LXI\LXIRef\RefDesign_V01.00\Software\Solution\TestWebServer\TestWebServer.obj TestWebServer
Error 3 error LNK1120: 1 unresolved externals D:\LXI\LXIRef\RefDesign_V01.00\Software\Solution\Debug\TestWebServer.exe 1 1 TestWebServer
Give definitions to constructor and destructor.
#include <iostream>
class t1
{
public:
~t1() {} // <<<< defined here
static t1& fun();
private:
t1() {} // << defined here
};
t1& t1::fun()
{
return t1();
}
int main()
{
t1::fun();
return 0;
}
I am trying to create a custom List in c++.
I've defined it this way:
List.h:
#include "ListItem.h"
#pragma once
template<class T> class List
{
private:
ListItem<T>* first;
public:
T* GetAt(int);
ListItem<T>* GetLastListItem();
void Add(T*);
void Clear();
};
List.cpp:
#include "stdafx.h"
#include "List.h"
template<class T> T* List<T>::GetAt(int index)
{
if (!first)
return 0;
ListItem<T>* current = first;
for (int i = 1; i < index; i++)
{
current = current->GetNext();
}
return current->GetItem();
}
template<class T> L...
main:
List<TestItem> liste;
TestItem ti; //just a int inside.
liste.Add(&ti);
I am getting the following errors:
1>ConsoleApplication1.obj : error LNK2019: unresolved external symbol ""public: void __thiscall List::Add(class TestItem *)" (?Add#?$List#VTestItem####QAEXPAVTestItem###Z)" in function"_main".
This question already has answers here:
Why can templates only be implemented in the header file?
(17 answers)
Closed 7 years ago.
I am trying to figure out how to use classes with class template and I get these errors:
Error 1 error LNK2019: unresolved external symbol "public: __thiscall AdtBag::AdtBag(void)" (??0?$AdtBag#H##QAE#XZ) referenced in function _main C:\Users\User\Documents\Visual Studio 2013\Projects\ADTBagAddition\ADTBagAddition\Source.obj ADTBagAddition
Error 2 error LNK2019: unresolved external symbol "public: __thiscall AdtBag::~AdtBag(void)" (??1?$AdtBag#H##QAE#XZ) referenced in function _main C:\Users\User\Documents\Visual Studio 2013\Projects\ADTBagAddition\ADTBagAddition\Source.obj ADTBagAddition
Error 3 error LNK2019: unresolved external symbol "public: void __thiscall AdtBag::store_in_bag(int)" (?store_in_bag#?$AdtBag#H##QAEXH#Z) referenced in function _main C:\Users\User\Documents\Visual Studio 2013\Projects\ADTBagAddition\ADTBagAddition\Source.obj ADTBagAddition
Error 4 error LNK2019: unresolved external symbol "public: int __thiscall AdtBag::whats_in_bag(void)" (?whats_in_bag#?$AdtBag#H##QAEHXZ) referenced in function _main C:\Users\User\Documents\Visual Studio 2013\Projects\ADTBagAddition\ADTBagAddition\Source.obj ADTBagAddition
Error 5 error LNK1120: 4 unresolved externals C:\Users\User\Documents\Visual Studio 2013\Projects\ADTBagAddition\Debug\ADTBagAddition.exe ADTBagAddition
Here is my code:
source.cpp
#include <iostream>
#include "AdtBag.h"
using namespace std;
int main () {
AdtBag<int> BagInt;
int a = 78;
cout << "Int Bag Contains: " << endl;
BagInt.store_in_bag ( a );
cout << BagInt.whats_in_bag () << endl;
return 0;
}
AdtBag.h
#ifndef __ADTBAG__
#define __ADTBAG__
template<class ItemType>
class AdtBag {
private:
ItemType in_bag;
public:
AdtBag<ItemType> ();
~AdtBag<ItemType> ();
void store_in_bag ( ItemType into_bag );
ItemType whats_in_bag ();
};
#endif
AdtBag.cpp
#include "AdtBag.h"
template <class ItemType>
AdtBag<ItemType>::AdtBag () {
}
template <class ItemType>
AdtBag<ItemType>::~AdtBag () {
}
template<class ItemType>
void AdtBag<ItemType>::store_in_bag ( ItemType into_bag ) {
in_bag = into_bag;
}
template<class ItemType>
ItemType AdtBag<ItemType>::whats_in_bag () {
return in_bag;
}
Why is this producing the error messages? I'm using Visual Studio 2013 if that matters. I thought I did everything correctly, but I guess not. Any suggestions?
Loosely speaking, all template class code must be in the header.
Essentially, this is because template code is only compiled when a template is instantiated for some type.
I created a templated data class (CAnyData, please see its header file copy for your reference), with which I declared some variables in my another class (CConstantDataBlock, please see its header file copy for your reference). As you may see, the latter one is nearly an empty class. But when I compiled my project, the VS2008 compiler thowed the following linking errors. Would please help me figure out what's wrong with my CConstantDataBlock and/or CAnyData?
1>------ Build started: Project: Tips, Configuration: Debug Win32 ------
1>Compiling...
1>ConstantDataBlock.cpp
1>Linking...
1> Creating library F:\Tips\Debug\Tips.lib and object F:\Tips\Debug\Tips.exp
1>ConstantDataBlock.obj : error LNK2019: unresolved external symbol "public: __thiscall CAnyData<double>::~CAnyData<double>(void)" (??1?$CAnyData#N##QAE#XZ) referenced in function __unwindfunclet$??0CConstantDataBlock##QAE#XZ$0
1>ConstantDataBlock.obj : error LNK2019: unresolved external symbol "public: __thiscall CAnyData<int>::~CAnyData<int>(void)" (??1?$CAnyData#H##QAE#XZ) referenced in function __unwindfunclet$??0CConstantDataBlock##QAE#XZ$0
1>ConstantDataBlock.obj : error LNK2019: unresolved external symbol "public: __thiscall CAnyData<double>::CAnyData<double>(void)" (??0?$CAnyData#N##QAE#XZ) referenced in function "public: __thiscall CConstantDataBlock::CConstantDataBlock(void)" (??0CConstantDataBlock##QAE#XZ)
1>ConstantDataBlock.obj : error LNK2019: unresolved external symbol "public: __thiscall CAnyData<int>::CAnyData<int>(void)" (??0?$CAnyData#H##QAE#XZ) referenced in function "public: __thiscall CConstantDataBlock::CConstantDataBlock(void)" (??0CConstantDataBlock##QAE#XZ)
1>F:\Tips\Debug\Tips.exe : fatal error LNK1120: 4 unresolved externals
1>Build log was saved at "file://f:\Tips\Tips\Debug\BuildLog.htm"
1>Tips - 5 error(s), 0 warning(s)
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========
#pragma once
#include <string>
using namespace std;
template <class T>
class CAnyData
{
public:
CAnyData(void);
CAnyData(int nWordNumber, string sContents, T Type, int nWidth, int nPrecision);
~CAnyData(void);
// Operators
CAnyData( const CAnyData& rhs );
const CAnyData& operator = (const CAnyData& rhs);
// Must define less than relative to name objects.
bool operator<( const CAnyData& AnyData ) const;
// Compares profile's of two objects which represent CAnyData
inline bool operator ==(const CAnyData& rhs) const;
// Get properties
inline int WordNumber() const { return m_nWordNumber; }
inline const string& Contents() const { return m_sContents; }
inline const T& DataType() const { return m_Type; }
inline int Width() const { return m_nWidth; }
inline int Precision() const { return m_nPrecision; }
// Set properties
void WordNumber(int nWordNumber) const { m_nWordNumber = nWordNumber; }
void Contents(string sContents) const { m_sContents = sContents; }
void DataType(T Type) const { m_Type = Type; }
void Width(int nWidth) const { m_nWidth = nWidth; }
void Precision(int nPrecision) const { m_nPrecision = nPrecision; }
protected:
void Init(void);
protected:
int m_nWordNumber;
string m_sContents;
T m_Type;
int m_nWidth;
int m_nPrecision;
};
#pragma once
#include "AnyData.h"
// Constants block
// This block consists of 64 words to be filled with useful constants.
class CConstantDataBlock
{
public:
CConstantDataBlock(void);
~CConstantDataBlock(void);
protected:
CAnyData<int> m_nEarthEquatorialRadius;
CAnyData<int> m_nNominalSatelliteHeight;
CAnyData<double> m_dEarthCircumference;
CAnyData<double> m_dEarthInverseFlattening;
};
It seems that you do not have definitions for several of the methods of CAnyData, including the default constructor and the destructor. When you use these in your CConstantDataBlock-class, the constructor and destructor are required though.
Since CAnyData is a class-template, all definitions should be written directly into the header-file (just as you have done with all the getters and setters).
PacketBuilder is a little Class which allow to write into a char* array. The Append Functions:
template <class T>
void PacketBuilder::Append(const T value)
{
memcpy((&m_Buffer) + m_Index, (const void*) &value, sizeof(T));
m_Index += sizeof(T);
}
Compiling without errors. If I call Append and use T as unsigned short (WORD). It works great. If I use T as unsigned char. I get an Linker Error.
m_Builder.Append<unsigned char>(0x01); // Error: LNK1120
m_Builder.Append<unsigned short>(0x0001); // Works
Error from VS2010 (sry i got german vs2010):
error LNK2019: Verweis auf nicht
aufgelöstes externes Symbol ""public:
void __thiscall
PacketBuilder::Append(unsigned char)"
(??$Append#E#PacketBuilder##QAEXE#Z)"
in Funktion ""public: void __thiscall
Client::DoHandshake(void)"
(?DoHandshake#Client##QAEXXZ)".
1>C:\XXX\C++\SilkroadEmu\Debug\LoginServer.exe
: fatal error LNK1120: 1 nicht
aufgelöste externe Verweise.
Translated to English:
error LNK2019: Unresolved external
symbol ""public: void __thiscall
PacketBuilder::Append(unsigned char)"
(??$Append#E#PacketBuilder##QAEXE#Z)"
in Function ""public: void __thiscall
Client::DoHandshake(void)"
(?DoHandshake#Client##QAEXXZ)".
1>C:\XXX\C++\SilkroadEmu\Debug\LoginServer.exe
: fatal error LNK1120: 1 unsresolved
external symbol.
Put the method definition in the header (hpp file), not in the implementation (cpp) file.
Your PacketBuilder is not a class template, as far as I can see. PacketBuilder::Append is however a template method, which requires that it's definition must be visible at any point of instantiation of this method. The only really safe way to assure this is to put the complete definition of this method template into the header file:
class PacketBuilder {
// declarations of non-template members
public:
template <class T>
void Append(const T value)
{
memcpy((&m_Buffer) + m_Index, (const void*) &value, sizeof(T));
m_Index += sizeof(T);
}
};