-
#include problem
Hi there,
I'm writing a simple snake game for a uni course, and I'm having a little trouble linking all the files together
I have 3 classes (Snake, AISnake and GameEvent) and a structure (Positions), Snake and GameEvent share a .hpp and .cpp file and Positions is located in the AISnake .hpp
If I #include AIsnake.hpp in snake.cpp then snake.hpp can't find the position structure
if I #include AIsnake.hpp in snake.hpp then I get an error saying there is not matching function for AISnake::AISnake(), but that function exists
If I #include AIsnake.hpp in both snake.cpp and snake.hpp then the compiler says I'm redefining structure and AIsnake class at the same place its defined in the first place.
I'm assuming that where I want to #include it is in the snake.hpp file, as that is giving me the least errors, and that error also appears when its included in both, which would suggest there's an error somewhere else, but I can't think what that would be, as I do have a function called AISnake::AISnake()
any help would be great.
Cheers
ES
P.S. If you need to see any code just give me a shout, I didn't include any here because I assume you all know what a #include looks like ;)
-
You need to use header guards, this way the preprocessor will filter out any header files that have already been included:
myheader.h:
Code:
#ifndef MYHEADER_H
#define MYHEADER_H
// CODE GOES HERE
#endif
Now you can (and should) include all headers where they are necessary (eg. #include <string> in all files where a std::string is being used.), the preprocessor will filter out all the duplicates and the compiler will never know a thing.
-
Thats exactly what my tutor told me, but I am using header guards.
I have the following guards in their respective files
Code:
#ifndef SNAKE_HPP_INCLUDED
#define SNAKE_HPP_INCLUDED
{code}
#endif
Code:
#ifndef AI_SNAKE_HPP_INCLUDED
#define AI_SNAKE_HPP_INCLUDED
{code}
#endif
sorry, I guess I should have mentioned that :-S
-
Alright well you should listen to your tutor then :-) Now with header guards you _should_ be able to include both those files whereever they are needed.
What you need to do is include the "AISnake.hpp" in "Snake.hpp", not in the .cpp file. You mention that this produces a compiler error, try to post the code from the AISnake constructor, and the entire error message.
-
I already had the header guards in when he told me to add them ;-)
anyway, heres the AISnake constrructor
Code:
AISnake::AISnake(int x = 0, int y = 0)
{
ImageFile("../Assets/node2.tga").load(nodeimage2);
AIsegments.push_front(Position(20,700));
AIsegments.push_front(Position(40,700));
AIsegments.push_front(Position(60,700));
direction_ = 'w';
}
and the compiler error reads:
No matching function to call to AISnake::AISnake()
Candidates are : AISnake::AISnake(int, int)
AISnake::AISnake(const AISnake&)
When I get this error it highlights the GamEvent constructor, which makes no mention of AISnake. I also checked and could find calling AISnake without the two ints.
heres the GameEvent constructor just so you can see
Code:
GameEvent::GameEvent() : t_(0,300,this)
{
}
-
It seems like you are declaring the constructor like this in the .hpp file:
Code:
class AISnake
{
public:
AISnake(int x = 0, int y = 0);
};
And then defining the constructor in the .cpp file like this:
Code:
AISnake::AISnake(int x = 0, int y = 0)
{
ImageFile("../Assets/node2.tga").load(nodeimage2);
AIsegments.push_front(Position(20,700));
AIsegments.push_front(Position(40,700));
AIsegments.push_front(Position(60,700));
direction_ = 'w';
}
Is this correct? If so, you need to remove the default assignments (x =0, y =0) from the definition in the .cpp file, default assignments should only go in the declaration, not in both the declaration and definition.
-
No, I haven't assigned x or y to anything in the .hpp file. I'm sorry I should probably have posted both the .hpp and .cpp versions on the constructor.
Although this was something I did earlier in the creation of the program ;-)
-
Your problem may be that you are using a class with a non-default constructor in another structure or class, and not providing a constructor for that class. In other words, unless the including class has a constructor which invokes the non-default constructor of a member, you will get this error because the compiler tries to invoke a default constructor which doesn't exist.
In other words, this:
Code:
struct A
{
A( int ) {}
};
struct B
{
A a;
};
If you compile that, you will get a similar error. The solution is to add a constructor to B which calls A( int ).