假设我们需要编写一个我们打算在程序中使用的函数库,然后我们可以通过以下方式编写它。
在.h文件中我们声明了该函数(mylibrary可以是我们希望的任何文件名) 假设sum是我们希望在库中的函数
int sum(int x, int y);
然后我们将有一个.cpp文件,它将定义函数如下:
#include "mylibrary.h"
int sum(int x, int y){ return x+y; }
现在我们希望在我们的程序中使用这个函数,比如myprog.cpp,我们可以这样使用:
#include
#include "mylibrary.h"
int main()
{
cout<<sum(10,20)<<endl;
return 0;
}
我的问题是,我们可以为类做类似的功能,即
我们可以在.h文件中声明类,如:
class X;
class Y;
然后在.cpp中定义类,如:
#include"myclasses.h"
class X
{
public:
int m;
};
class Y
{
public:
int n;
};
然后在我们的程序中使用这些类,比如myprog.cpp,就像这样:
#include"myclasses.h"
int main()
{
class X myX;
myX.m = 0;
return 0;
}
我试过这个并得到错误聚合'X myX'类型不完整且无法定义。
如果我将整个定义放在myclasses.h文件中,那么它运行正常而没有错误。
我想知道我们是否可以按照函数库的蓝图编写一个类库。
我尝试过:
如果我将整个定义放在myclasses.h文件中,那么它运行正常而没有错误。
我想知道我们是否可以按照函数库的蓝图编写一个类库。enter code here
答案 0 :(得分:3)
您可以将所有方法放在.cpp
文件中,但您必须拥有&#34;完整的&#34;头文件中类的声明。也就是说,你可以这样做:
// X.h
#ifndef _X_H
#define _X_H
class X {
int data;
void internal_method();
public:
void foo();
void bar();
};
#endif // X.h
然后您可以在X::foo
文件中定义X::bar
,X::internal_method
和.cpp
,但您无法执行此操作或类似操作:< / p>
// X.h
#ifndef _X_H
#define _X_H
// This code is incorrect and will not even compile
class X;
public void X::foo();
public void X::bar();
#endif // X.h
这是C ++的一个基本限制,是的,它意味着您无法重新编译数据成员或添加或删除方法 - 甚至是私有方法 - 而无需重新编译所有内容。 pimpl hack解决了这个问题,但也存在问题。
(你可能已经注意到class X;
本身 是一个有效的东西。这是一个&#34;不完整的&#34;类的声明,它允许你将涉及指针和引用的内容声明为X对象,而不是X对象本身。例如,此头文件 有效:
// Y.h
#ifndef _Y_H
#define _Y_H
class X;
class Y {
X& ex;
public:
Y(X& ex) : ex(ex) {}
void foo();
void bar(X& fx);
};
#endif // Y.h
这可能是一件很有用的事情,例如减少需要包含其他头文件的头文件的数量,以及打破相互依赖循环(假设class X
有一些方法需要引用到Y的参数,没有像这样的特征你根本就不能写这个。)
答案 1 :(得分:0)
是的,你可以这样做; 但类的完整声明 - 类似于声明函数 - 涉及声明其所有成员。 (有关详细信息,请参阅http://en.cppreference.com/w/cpp/language/class,但我知道您已经熟悉它们。)
如果您只是&#34;转发声明&#34;这个类,通过编写class Foo;
而没有完全声明它,那么你仍然可以传递指向它的指针,但是你不能引用它的任何成员,包括它的构造函数(甚至是编译器生成的成员,因为那些没有无条件生成;并非所有类都有它们)。请注意,前向声明甚至不足以告诉编译器实例的大小(sizeof
)。