Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
612 views
in Technique[技术] by (71.8m points)

c++ - #pragma once and #include issues

I had an issue of circular references (i.e. A.h and B.h #including each other) and some people advised me to use #pragma once to prevent that. However, this solution appears to be not working still.

What's happening is that class A no longer becomes recognized in any file other than A.h (not even in A.cpp) and the same happens for class B.

Let me show you the code:

A.h

#pragma once
#include "B.h"

class A {
public: B* b;

};

B.h

#pragma once
#include "A.h"

class B {
    public: A* a;
};

A.cpp

#include "stdafx.h"
#include "A.h"
#include "B.h"

B.cpp is same as A.cpp

The error trace reads as followed:

1> B.cpp 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C2143: syntax error : missing ';' before '' 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C4430: missing type specifier - int assumed. Note: C++ does not support default-int 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C4430: missing type specifier - int assumed. Note: C++ does not support default-int 1> A.cpp 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C2143: syntax error : missing ';' before '' 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C4430: missing type specifier - int assumed. Note: C++ does not support default-int 1>c:usersuserdocumentsvisual studio 2010projectsenvmodel est.h(5): error C4430: missing type specifier - int assumed. Note: C++ does not support default-int

There are two more things I'd like to clarify:

  1. How and when to use #include "stdafx.h" in Visual Studio 2010 (I really hate this IDE, but it appears to be the only one that works well with C++ - Netbeans is total trash with this language)

  2. How to use #pragma once correctly? I'd assume I'd just put it at the first line of each file (well, obviously that doesn't solve my problems!). Also, should it be placed before or after #include "stdafx.h"? Note: I didn't put #pragma once in stdafx.h

Thanks.

Edit: I forgot the semi-colons, thus the original error trace was bloated. Edit2: I forgot to use pointers. My actual program did use pointers instead of plain object values and I neglected that in my haste to create a small example.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You can't have circular dependencies.

Think of it like this. If you instanciate an object of type A; then how big is it? The answer is infinitely large. So you can't create objects that are circular like that anyway.

You need to break the cycle with an optional value (a pointer).
SO If you change B to hold a pointer to A and use forward references then it works.

#pragma once
class A; // Forward reference.

class B {
    public: A* a; // Break cycle with a pointer. (In real life use a smart pointer)
}

Note: You should still use the #pragma once in your header files.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...