Reputation: 1099
I have a Main.cpp and Example.cpp files.
This might be bad what I did, since I'm new to c++, but here is the code I wrote inside my Example.cpp:
#include <iostream>
namespace example {
using namespace std;
void myfunc1() {
cout << "func1" << endl;
}
void myfunc2() {
cout << "func2" << endl;
}
}
So, I came to an idea to call that namespace inside Main.cpp:
#include <iostream>
using namespace example;
int main() {
return 0;
}
Now I have a problem to call "example" namespace from another file. Do I need to create a header for that cpp file ?
Upvotes: 0
Views: 1145
Reputation: 1899
Here's how you should do. You should declare your functions which are intended to be included in a namespace in a single header file, and then include it in every cpp file which needs it. The implementations of your "namespaced" functions should be in a single cpp file too. With your example, this should be as followed.
example.hh :
#ifndef __EXAMPLE_HH__
# define __EXAMPLE_HH__
namespace example
{
void myfunc1();
void myfunc2();
}
#endif
example.cpp :
#include <iostream>
#include "example.hh"
void example::myfunc1()
{
std::cout << "func1" << std::endl;
}
void example::myfunc2()
{
std::cout << "func2" << std::endl;
}
Once your example namespace declared and implemented, you can use it as followed :
main.cpp :
#include "example.hh"
int main()
{
example::myfunc1();
example::myfunc2();
return (0);
}
Note that I don't use the using namespace
statement and that's why I need to write example::
before the name of my functions.
If you want not to have to write example::
each time, you can write using namespace example
but be careful : it doesn't not allow you to ommit the #include "example.hh"
preprocessor directive otherwise the compiler will not even know your example
namespace exists.
So remember : using namespace
doesn't stand for a #include
directive.
An explanation about source files and header files.
In the example, you have 3 files : 1 header file (example.hh), and 2 source files (example.cpp, main.cpp). It's common (because useful) to declare namespaces, classes, structures, functions ... in a header file, and include this header file in every source file which needs to use one of thoses previously defined names.
Why ? To allow the compiler to know about those names. Here, to make you executablefile , there are two steps :
Step 1 : compile every single source file to a corresponding object file, i.e make an example.o
file from your example.cpp
file. The example.o
file will contain byte code (here, the code of your example::myfunc1
and example::myfunc2
functions) and the main.o
the code for the main
function.
These object files are made by a compiler. For example, you make an object file with GCC (G++ for C++) as followed : g++ -c -o example.o example.cpp
.
It's here that the header files are useful. When your example.cpp
file is read by GCC, GCC reads the #include "example.hh"
statement which tells him to read example.hh
too, and that's how GCC can know about your namespace and its functions.
example.cpp
, if you had not included your header file, GCC would have read void example::myfunc1() { ... }
and you would have thrown an error telling you something like Unknown namespace
depending on the compiler you use.main.cpp
, you would have got another error telling you that the namespace was not found.What is interesting in the way of doing is that in the compile main.o
, the byte code roughly says call myfunc1 from the example namespace, then call myfunc2 from the example namespace
but it DOES NOT include the code for these 2 functions in main.o
file.
So when GCC reads the function calls, it does not know their implementation but it knows them from the header file. Roughly, declaring them in the header file and include it in the source files tells GCC something like This namespace and its functions exist, they will be implemented somewhere else
.
So here, you have your 2 corresponding object files : main.o
and example.o
.
Step 2 : take all object files you've just made to link them and make an executable. Again, with GCC : gcc -o exampleExcutable main.o example.o
. That's where the magic happens : the linker see that there's a call to example::myfunc1
and example::myfunc2
, finds their implementation in example.o
, and is able to create your executable file.
Here you get your executable file exampleExecutable
, you run it and get your expected output :
$ ./exampleExecutable
func1
func2
To concude, header files are used to declare symbols and to be included in source files. When sources files are compiled, the corresponding object files don't contain the definition of these declared symbols, but they're resolved during link time.
Upvotes: 4
Reputation: 36082
In order for the compiler/linker to know which function you are referring to it needs the prototype of the functions.
Create a header for your namespace e.g.
#ifndef EXAMPLE_H
#define EXAMPLE_H
namespace example
{
void myfunc1();
void myfunc2();
};
#endif
Then include the header in example.cpp and in your main.cpp
Upvotes: 1