Can you explain me why my function AllToAll is undefined in my example? I use CMake to generate a libNeuralNetwork.a which is called by the exemple.
LayerFactory.hpp
#pragma once
#include "LayerModel.hpp"
#include "Layer.hpp"
namespace nn
{
extern internal::LayerModel AllToAll(int numberOfNeurons, activationFunction activation = sigmoid);
}
LayerFactory.cpp
#include "LayerFactory.hpp"
#include "AllToAll.hpp"
using namespace nn;
using namespace internal;
LayerModel AllToAll(int numberOfNeurons, activationFunction activation)
{
LayerModel model
{
allToAll,
activation,
numberOfNeurons
};
return model;
}
NeuralNetwork.hpp
#pragma once
#include "layer/LayerModel.hpp"
#include "layer/LayerFactory.hpp"
namespace nn
{
class NeuralNetwork
{
public:
NeuralNetwork(int numberOfInputs, std::vector<internal::LayerModel> models);
//...
};
}
Example.cpp
#include "../src/neural_network/NeuralNetwork.hpp"
using namespace nn;
int example1()
{
NeuralNetwork neuralNetwork(3, {AllToAll(5), AllToAll(2)});
}
error message:
CMakeFiles/UnitTests.out.dir/ExamplesTest.cpp.o: In function `example1()':
ExamplesTest.cpp:(.text+0x8b3): undefined reference to `nn::AllToAll(int, nn::activationFunction)'
You have declared AllToAll in the top-level namespace and defined it in the nn namespace.
The following will not declare the function in the namespace:
using namespace foo;
extern void Bar();
You need:
namespace foo {
extern void Bar();
}
Related
I cannot compile my C++ program and I don't understand why.
Here's a simple representation of what is throwing errors:
hello/hello.cpp
#include "hello.h"
namespace MyHelloNS {
MyHelloClass::MyHelloClass() {
MyHelloVAR1 = "hi";
MyHelloVAR2 = "dog";
}
}
hello/hello.h
#pragma once
#include <string>
using namespace std;
namespace MyHelloNS {
extern string MyHelloVAR1;
extern string MyHelloVAR2;
class MyHelloClass;
}
class MyHelloNS::MyHelloClass {
public:
MyHelloClass();
};
main.cpp
#include "hello/hello.h"
int main() {
MyHelloNS::MyHelloClass hi1;
}
I get two kinds of errors:
unresolved external symbol in hello.obj
What's wrong?
Add this to main.cpp (or hello.cpp)
namespace MyHelloNS {
string MyHelloVAR1;
string MyHelloVAR2;
}
This question has nothing to do with namespaces, you just aren't following the correct procedure to define a global variable.
I've created 2 header files. ListA.h and ListN.h
They both make their own use their own unique class List. When I compile my program (even though they have no way of knowing the other exists, it says the following error)
Im pretty sure it shouldnt be a redefinition, but it obviously is. Any help is appreciated.
ListA.h
#ifndef __LISTA_H_
#define __LISTA_H_
#include <iostream>
using namespace std;
class List{
public:
List(int = 0);
List(const List&);
~List();
};
#endif
ListN.h
#ifndef __LISTN_H_
#define __LISTN_H_
#include <iostream>
using namespace std;
class List{
public:
List(int = 10);
List(const List&);
~List();
};
#endif
ListA.cpp
#include "ListA.h"
using namespace std;
List::List(int mySize)
{
//...
}
ListN.cpp
#include "ListN.h"
#include <iostream>
using namespace std;
List::List(int size)
{
//...
}
Main
#include <iostream>
#include "ListN.h"
using namespace std;
int main()
{
List myList;
return 0;
}
Both cpp files are being compiled by the compiler. Thus, when the linker goes to link the files together, it gets confused, since there are multiple List classes.
To fix this, you could use namespaces, or you cold not expose at least one of the List classes.
Alternatively, if the idea was to be able to include ListN.h vs ListA.h for configuration purposes, this is the wrong way to do so. Either you should have a #define parameter for the header, or you should find some other way, such as through #ifdef. For example (I'm not 100% sure this would compile, but you get the idea):
List.h
#ifndef __LIST_H_
#define __LIST_H_
#ifndef LIST_PARAM
#define LIST_PARAM 0
#endif
#include <iostream>
using namespace std;
class List{
public:
List(int = LIST_PARAM);
List(const List&);
~List();
};
#endif
main.cpp
#include <iostream>
#define LIST_PARAM 10
#include "List.h"
using namespace std;
int main()
{
List myList;
return 0;
}
I personally don't like this method; it is much better to just pass the value in to the constructor:
int main()
{
List myList{ 10 };
return 0;
}
When linker trying to link find the definition / symbol for List, it does found in two different obj file and hence linker givers error. In visual studio error number : LNK2005
To solve this error, either:
To fix, add /FORCE:MULTIPLE to the linker command line options
Add the classes in two different namespaces which will avoid this error.
ListN.h
#ifndef __LIST_H_
#define __LIST_H_
#include <iostream>
using namespace std;
namespace ListN
{
class List{
public:
List(int = 10);
List(const List&);
};
}
#endif
ListN.cpp
#include "ListN.h"
#include <iostream>
using namespace std;
namespace ListN
{
List::List(int size)
{
//...
}
}
Main.cpp
#include <iostream>
#include "ListN.h"
int main()
{
ListN::List myList;
return 0;
}
I have a header file, RandFunctions.hpp which contains a template function,
#ifndef _RANDFUNCTIONS_HPP_
#define _RANDFUNCTIONS_HPP_
#include <stdlib.h>
#include <time.h>
namespace surena
{
namespace common
{
template<typename RealT> inline
RealT
RealRandom()
{
return rand()/(RealT(RAND_MAX)+1);
}
};
};
#endif
and another header file, Search.hpp which includes RandFunctions.hpp,
#ifndef _SEARCH_HPP_
#define _SEARCH_HPP_
#include "RandFunctions.hpp"
#include <stdlib.h>
#include <time.h>
namespace surena
{
namespace search
{
template<typename RealT>
class CTest
{
public:
CTest() {srand((unsigned)(time(0)));}
RealT
GenRand(){ return common::RealRandom(); }
};
};
};
#endif
when I include Search.hpp in a cpp file, for example,
#include "Search.hpp"
int
main(int argc, char** argv)
{
CTest<float> test;
return(0);
}
I get the following compile time error:
‘RealRandom’ is not a member of ‘surena::common’
What is wrong here?
Since RealRandom is a template function with no parameters, you need to provide a template argument:
GenRand(){ return common::RealRandom<RealT>(); }
^^^^^^^
Also in your main you'd have to qualify your test variable with the proper namespaces:
surena::search::CTest<float> test;
^^^^^^^^^^^^^^^^
Hi i just created a sample class and using it in main but i am getting already defined error.
sample.h
#ifndef __sample__
#define __sample__
#include<iostream>
using namespace std;
int count = 10;
class sample
{
public:
sample();
int Get();
private:
int i;
};
#endif
sample.cpp
#include "sample.h"
sample::sample()
{
cout<<"hello two";
}
int sample::sample()
{
return 10;
}
main.cpp
#include <iostream>
#include "sample.h"
using namespace std;
int main(void)
{
int test = count;
return 0;
}
Link error:
main.obj : error LNK2005: "int count" (?count##3HA) already defined in sample.obj
if u see above class i am using #ifndef and #define, actually there things will declare data once thought we include in many places.could some one explain me clearly why its giving that link error.
Remember that #include literally means "add the contents of this file here".
Include guards only protects against a file's content being included more than once per file it's included in.
When the preprocessor has done its preprocessing, this is what your compiler sees:
sample.cpp
[iostream contents here...]
using namespace std;
int count = 10;
class sample
{
public:
sample();
int Get();
private:
int i;
};
sample::sample()
{
cout<<"hello two";
}
int sample::sample()
{
return 10;
}
main.cpp
[iostream contents here...]
using namespace std;
int count = 10;
class sample
{
public:
sample();
int Get();
private:
int i;
};
using namespace std;
int main(void)
{
int test = count;
return 0;
}
As you can see, there are two definitions of count, one in each file (formally, "translation unit").
The solution is to have a declaration of the variable in "sample.h"
extern int count;
and have the one and only definition in sample.cpp:
int count = 10;
(And you should not put using namespace std; in a header.)
To make a global variable like that visible everywhere:
blah.h
extern int count;
blah.cpp
int count(10);
Include guards only guard against including the same header file multiple times, not against multiple definitions. You should move your variable in a cpp file in order to not violate the ODR, or use internal linkage or declare it external and define it somewhere once. There are multiple solutions depending on the use of that variable.
Notice that I'm ignoring the fact that you probably meant int sample::Get() in the sample.cpp file
#include "sample.h"
sample::sample()
{
cout<<"hello two";
}
int sample::sample() // ??
{
return 10;
}
You have either to declare variable count as having internal linkage as for example
#ifndef __sample__
#define __sample__
#include<iostream>
using namespace std;
namespace
{
int count = 10;
}
//...
#endif
(the above internal declaration valid in C++ 2011) or
#ifndef __sample__
#define __sample__
#include<iostream>
using namespace std;
static int count = 10;
//...
#endif
Or to declare it as having external linkage but define it only once in some module. Fpr example
#ifndef __sample__
#define __sample__
#include<iostream>
using namespace std;
extern int count;
//...
#endif
#include "sample.h"
int count = 10;
sample::sample()
{
cout<<"hello two";
}
int sample::sample()
{
return 10;
}
Otherwise the compiler will issue an error that variable count is defined more than once that is that more than one compilation unit (in this case sample.cpp and main.cpp) contain the variable definition.
I am farily new to C++ and I have been stuck with this problem for a few hours now. I am trying to setup the foundations for a video game related experience calculator, but I can't get past this problem.
main.cpp
#include <iostream>
#include "Log.h"
using namespace std;
int main()
{
Log Logs;
enter code here
struct ChoppableLog Yew;
Logs.initialiseLog(Yew, 60, 175);
return 0;
}
Log.h
#ifndef LOG_H
#define LOG_H
struct ChoppableLog
{
int level;
int xp;
};
class Log
{
public:
void initialiseLog(struct ChoppableLog &par1_log, int par2_int, int par3_int);
Log();
};
#endif // LOG_H
Log.cpp
#include "Log.h"
#include <iostream>
using namespace std;
Log::Log()
{
}
void initialiseLog(struct ChoppableLog &par1_log, int par2_int, int par3_int)
{
}
The error I get is
C:\Users\Murmanox\Documents\C++\C++ Projects\CodeBlocks\Class Files Test\main.cpp|11|undefined reference to `Log::initialiseLog(ChoppableLog&, int, int)'|
I can post more details if necessary.
You have to define Log::initialiseLog with its full name, like so:
void Log::initialiseLog(struct ChoppableLog &par1_log, int par2_int, int par3_int)
{ }
What you are doing is defining a new, free function of the name initialiseLog instead of defining the member function of Log.
This leaves the member function undefined, and, when calling it, your compiler (well, technically linker) will be unable to find it.
The definitions of functions in a header file should specify the scope. In your case, you should define initialiseLog() function in your cpp file as follows:
void Log::initialiseLog(struct ChoppableLog &par1_log, int par2_int, int par3_int)
{
}