Thread: "is not a class or namespace name" error

  1. #1
    Registered User
    Join Date
    Sep 2011
    Posts
    25

    Question "is not a class or namespace name" error

    Hi guys,

    I'm trying to figure out why this piece of code, while simple, just refuses to compile in Visual C++ 2010. I have these three example files (two headers, and one main CPP code file). I'd like to use an enum defined in one of the header files (main.h) as a return type for a function in the other (foo.h).

    main.h:
    Code:
    #ifndef __MAINHEAD
    #define __MAINHEAD
    
    #include "foo.h"
    
    class main
    {
    public:
    	enum aNewEnum {red, white, blue};
    };
    
    #endif
    foo.h:
    Code:
    #ifndef __FOOHEAD
    #define __FOOHEAD
    
    #include "main.h"
    
    class foo
    {
    public:
    	main::aNewEnum FunkyFunction();
    };
    
    #endif
    main.cpp:
    Code:
    #include <iostream>
    #include <string>
    #include "main.h"
    
    int main()
    {
    	std::cout << "hello world";
    	return 0;
    }
    When I try to build the project, I get error C2653: 'main' : is not a class or namespace name...

    I don't think the problem is due to main.cpp, or any of the files for that matter. I feel this should work, but isn't because of something the compiler is missing. Can anyone shed some light on this?

  2. #2
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    It looks like you have a name collision: you have a class in the global namespace named main, but the global main function is also named main (duh). Rename your class, or use your own namespace.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #3
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    Ah, I can see how that could be a problem. Stupid mistake on my part. However, after renaming main and correcting all relative lines to a new name "newtest", the error still occurs. Any other insight?

  4. #4
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Oh, I did not notice this earlier, but you also have a circular include problem: main.h includes foo.h which includes main.h

    It looks like main.h does not need to include foo.h, so remove that header inclusion.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  5. #5
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    Do circular include problems exist even though I have #ifndefs present in both headers?

    Also, what if main/newtest has a datamember that needs something from foo? A method that requires the output from foo.FunkyFunction perhaps? Is there some way to satisfy the dependence of foo on main AND main on foo at the same time without running into this circular include problem?

    (PS, thank you so much for your quick and helpful replies)

  6. #6
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by blakeo_x
    Do circular include problems exist even though I have #ifndefs present in both headers?
    Kind of. What is happening here is that when main.h is included, it includes foo.h. foo.h includes main.h, but due to the guard, that include effectively does not happen. Now, you use the class name for the enum... but the class has not been defined yet because it will only be defined later in main.h.

    Quote Originally Posted by blakeo_x
    Also, what if main/newtest has a datamember that needs something from foo? A method that requires the output from foo.FunkyFunction perhaps? Is there some way to satisfy the dependence of foo on main AND main on foo at the same time without running into this circular include problem?
    If feasible, you would use a forward declaration instead of including the header. Otherwise, you may have to re-design.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  7. #7
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    I think I get it now. Thanks for taking the time to help me out! It looks like I'll just have to redesign my program. I'm thinking separate the enum from the other two classes/headers.

    I have one quick, semi-related question involving enums that are public datamembers of other classes. To keep things simple, use the previous program as an example and supposing the previous error did not apply, how could I make FunkyFunction return aNewEnum's blue value? The two ways I originally thought would work were along the lines of:

    Code:
    enums::aNewEnum FunkyFunction() { return main::aNewEnum::blue; }
    
    - OR -
    
    enums::aNewEnum FunkyFunction() { return main::aNewEnum.blue; }
    Neither of these work. As you can tell, I'm not very sure when to use :: and when to use . . (still sort of new to C++) What is the correct way to do this?
    Last edited by blakeo_x; 09-16-2011 at 02:40 AM.

  8. #8
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    The first version should work.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  9. #9
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    I separated the enum to its own header/class named enumdefs. When I try the first version, I get warning C4482: nonstandard extension used: enum 'enumdefs::aNewEnum' used in qualified name.

    And the second gives me warning C4832: token '.' is illegal after UDT 'enumdefs::aNewEnum'.

    I added an include to enumdefs.h to both foo and main. Is this causing the same problem as before?
    Last edited by blakeo_x; 09-16-2011 at 02:51 AM.

  10. #10
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Post the smallest and simplest program that demonstrates the problem.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  11. #11
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    enumdefs.h:
    Code:
    #ifndef __ENUMS
    #define __ENUMS
    
    class enumdefs
    {
    public:
    	enum aNewEnum {red, white, blue};
    };
    
    #endif
    newtest.h:
    Code:
    #ifndef __MAINHEAD
    #define __MAINHEAD
    
    #include "enumdefs.h"
    
    class newtest
    {
    public:
    	enumdefs::aNewEnum GetFoo() { return enumdefs::aNewEnum::blue; };
    };
    
    #endif
    newtest.cpp:
    Code:
    #include <iostream>
    #include <string>
    #include "newtest.h"
    
    int main()
    {
    	newtest TestObj;
    	enumdefs::aNewEnum tempValue = TestObj.GetFoo();
    
    	std::cout << "Hello world, my favorite color is " << tempValue;
    	return 0;
    }
    This will not build. warning C4482: nonstandard extension used: enum 'enumdefs::aNewEnum' used in qualified name

  12. #12
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    WOOPS! Disregard that. It was just a warning message, and it did in fact build, and it does in fact execute. I apologize.

    At any rate, thank you very much for your patience and assistance in helping me! Problem solved.

  13. #13
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Oh, it should be:
    Code:
    return enumdefs::blue;
    Incidentally, enumdefs should probably be a namespace rather than a class.

    Also, note that names that begin with an underscore followed by an uppercase letter, or that contain consecutive underscores, are reserved to the implementation for any use. Therefore, do not use __ENUMS as a header inclusion guard name.
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  14. #14
    Registered User
    Join Date
    Sep 2011
    Posts
    25
    Oh wow, that works too! Did I mention I'm new to C++? Thanks again for the tips.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. the operator "="error in class "String"
    By boyhailong in forum C++ Programming
    Replies: 9
    Last Post: 07-27-2011, 08:39 PM
  2. Getting "undeclared member" error with derived class
    By indigo0086 in forum C++ Programming
    Replies: 4
    Last Post: 10-07-2007, 06:41 AM
  3. Getting a:"member is not of class type" error
    By indigo0086 in forum C++ Programming
    Replies: 10
    Last Post: 11-20-2006, 10:19 AM
  4. "itoa"-"_itoa" , "inp"-"_inp", Why some functions have "
    By L.O.K. in forum Windows Programming
    Replies: 5
    Last Post: 12-08-2002, 08:25 AM
  5. "CWnd"-"HWnd","CBitmap"-"HBitmap"...., What is mean by "
    By L.O.K. in forum Windows Programming
    Replies: 2
    Last Post: 12-04-2002, 07:59 AM