error C2011: 'Time' : 'class' type redefinition

Hi,

I'll just give a description of the project I'm working on right now. There are five files. Below are some descriptions and the first few lines of each:

Set.h -- contains the class definition of the Set class. The Set class has a private array of Time objects (see below), and various methods to manipulate that array.

1
2
3
#include <iostream>
#include "Time.h"
using namespace std;



Set.cpp -- contains the definitions for the member functions of the Set class (which is defined in Set.h).

1
2
3
4
#include <iostream>
#include "Set.h"
#include "Time.h"
using namespace std;



Time.h -- contains the class definition of the Time class, which works perfectly fine on it's own. Basically, it represents a time with three int values -- hour, minute, and second.

1
2
#include <iostream>
using namespace std;



Time.cpp -- contains the definitions for the member functions of the Time class (which is defined in Time.h)

1
2
3
#include <iostream>
#include "Time.h"
using namespace std;



setDriver.cpp -- the driver for the Set class. It calls and tests all the methods of the Set class.

1
2
3
4
#include <iostream>
#include "Set.h"
#include "Time.h"
using namespace std;



Once again, the Time class works fine on its own, and the Set class, when modified to use an array of int values instead of Time objects, works fine on its own. It's only when I modify things to create what you see above do I get this from Visual C++ 2008:

1
2
3
4
5
6
7
8
9
10
11
12
13
1
1>Compiling...
1>Set.cpp
1>c:\users\josh\documents\visual studio 2008\projects\set\set\time.h(112) : error C2011: 'Time' : 'class' type redefinition
1>        c:\users\josh\documents\visual studio 2008\projects\set\set\time.h(112) : see declaration of 'Time'
1>SetDriver.cpp
1>c:\users\josh\documents\visual studio 2008\projects\set\set\time.h(112) : error C2011: 'Time' : 'class' type redefinition
1>        c:\users\josh\documents\visual studio 2008\projects\set\set\time.h(112) : see declaration of 'Time'
1>c:\users\josh\documents\visual studio 2008\projects\set\set\setdriver.cpp(21) : error C3861: 'Time': identifier not found
1>Time.cpp
1>Generating Code...
1>Build log was saved at "file://c:\Users\Josh\Documents\Visual Studio 2008\Projects\Set\Set\Debug\BuildLog.htm"
1>Set - 3 error(s), 0 warning(s)
========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========


Does anyone know what this means?
The problem is that the Time.h file is being #included into the setDriver file twice. Keep in mind that the #include directive substitutes the code from the specified file at the top. Note how the Set.h file has a #include Time.h in it. When you #include Set.h into the setDriver.cpp file, it will substitute the code from that file into the setDriver.cpp file. Since Set.h already includes the Time.h file, that is substituted as well. You are then doing a #include Time.h in the setDriver.cpp file. So in the setDriver.cpp file, the compiler sees the Time.h definition twice:

1
2
3
//code for Time.h
//code for Set.h
//code for Time.h 


Essentially the compiler thinks there are two definitions for the Time.h function, and that isn't allowed. (Even though they're identical.) To remedy the problem try redoing the #inclusions statements like this:

1
2
3
4
#ifndef time_h
#define time_h
#include time.h
#endif 


This is a useful way to do all the file inclusions. What it says is that if time_h (name arbitrarily chosen as a representative of time.h) hasn't been defined, then execute the statements until it reaches the #endif. The statements then define time_h so that if this is encountered in, say, another file with a similar style of inclusion, it will see it as already defined, and thus will not #include it again.

I hope that's clear. If it's not, post back and let me know.
Last edited on
It's fine! My problem was solved, and I was able to complete the project. Thanks for the help!
Couldnt you just get rid of the #include Time.h in the Set.cpp and setDriver.cpp classes? If not, could someone post what the full header would look like according to gzero's instructions? Thanks.

And I apologize if Im not supposed to bump older threads. Just let me know, Im new. Thanks again.
The answer depends on what's in the code in each of the files. I think the best way to illustrate the point is with an example:

Say I have been tasked to create a computer model of a solar system. Say I have created a class called Matter, which describes properties of matter in it's various states. I then create another class called World. A world contains Matter, so I embed it in the definition of World and include it at the top. I then proceed to create a class called Moon. A moon also contains Matter, so once again I embed the class Matter into the definition of Moon, and include it at the top. Now I want to create a solar system using my newly designed objects, so I create a new file called Solarsystem, which contains my main() function to start the program. Obviously, in order to use both my World and my Moon in the Solarsystem, they will both have to be included into the Solarsystem file. When I do that, the compiler will complain that I've defined the Matter class twice. How to fix it? Well there are two solutions:

1) Solution 1 is what you proposed doing above: I could delete the #include "Matter.h" statements from both World and Moon, and then put #include Matter.h" at the top of my Solarsystem file. This will work, but it poses a potentially annoying problem. In order for this to work you have to keep all your file dependencies in order. Since Matter is embedded into World and Moon, they depend on Matter to function properly. The compiler reads things straight through from top to bottom, so in order to avoid generating an error it will have to encounter the definition of Matter before World or Moon. That means that I'll have to remember to put the #include "Matter.h" statement before the #include "World.h" and #include "Moon.h". This may not seem like such a big deal in a small program, but you can see where this would become a massive headache in a larger program that included many other files, all with there own file dependencies. It also makes your code more difficult for others to use, because they have to know all these file dependencies so they can include things in the proper order.

2) Solution 2 is what I have described above. With this method, the compiler is automatically checking to see if another file has already been included. (Or more accurately for the method above, defined.) In this case, for my Solarsystem function to use World and Moon, all I have to do is include them both, and the compiler will take care of making sure that Matter isn't defined twice. To do this the inclusion statements for the example I've illustrated would look something like this:

1
2
3
4
5
//World.h file
#ifndef Matter_h       //Remember, this is an arbitrarily chosen name
#define Matter_h
#include "Matter.h"
#endif 


1
2
3
4
5
//Moon.h file
#ifndef Matter_h
#define Matter_h
#include "Matter.h"
#endif 


1
2
3
4
5
//Solarsystem.cpp file
#include <iostream>
using namespace std;
#include "Moon.h"
#include "World.h" 


Note that the inclusions can be done normally in the Solarsystem file, because all the other files already have the inclusion check included. Hence if I wanted to write yet another class, Orbit, that has both World and Moon embedded into it, I would be able to just add

#include "Orbit.h"

to the Solarsystem.cpp file. (Provided the World and Moon were included into Orbit as I outlined above.)

I hope this helps.
Last edited on
Topic archived. No new replies allowed.