我最近开始关注类'帮助函数'中static
关键字的使用。现在我理解你声明一个成员函数static
如果它不与任何数据成员交互,而只对传递给它的参数起作用 - 一种“保险”,它不会无意中改变类本身。
以前我模糊地意识到这种情况,并通过在表单中声明一个函数来做同样的主动“保护”:
const int function_name(int parameter_one, int parameter_two) const;
在函数名称阻止在该函数内部更改任何类数据成员之后,我的理解是const
。
我并没有真正看到差异,也没有为什么'静态'更好地实现了这种“保护”。显然,尽管掌握了基础知识,但我仍然缺少一些细微差别。有人可以向我解释这些代码使用的细微之处吗?
答案 0 :(得分:2)
区别很简单:
静态类成员在类上工作,而不在类的实例/对象上工作。实际上,您无法从静态方法访问任何数据成员。您只能访问静态成员(方法和属性)。从静态函数调用其他成员函数也是如此。它根本不起作用,因为静态成员不知道类实例,也不能调用任何非静态方法!
在引擎盖下,非静态成员函数始终是一个隐藏指针,该实例只是类本身视图中的this pointer
。静态成员不需要这种指针,也不能使用它。
如果调用静态方法,则无需创建实例。实际上,类只是一种命名空间。如果从实例变量或指向它的指针调用静态成员,结果与没有实例的结果相同!
必须注意静态变量。必须在对象文件中的某个类之外定义!通常,在创建类的实例时,将创建类的所有“普通”成员。静态变量没有实例,因此它必须存在于其他地方。这需要在某处进行手动定义,如示例中所示。如果头文件中有类,则无法在其中定义变量。只有声明在课堂内。该定义必须放在cpp文件中。如果您尝试在标题中定义变量,则可以为此标头文件包含尽可能多的实例,这会在链接时生成multiple definition errors
!
因为您特别要求保护对班级成员的访问权限: 静态方法可以访问类的静态变量,也可以编写它们。但是你不能将const限定用于静态方法!
class A
{
public:
static void Do() { cout << "stat var " << stat_var << endl; }
void Do2() const { cout << "var" << var << endl; }
A():var(100) {}
private:
static int stat_var;
int var;
};
int A::stat_var=9;
int main()
{
A a; // instance of A a
a.Do2(); // call a method with the instance a
A::Do(); // call the static method without any instance
a.Do(); // this looks like a call with a class instance, but it is not!!!
}
答案 1 :(得分:0)
static
成员和const
成员是不同的概念,用于不同的目的。
考虑以下课程:
class fred
{
int a;
public:
fred( int aa ) : a(aa) { }
int what( int b ) const
{
return a + b;
}
static int whatnot( fred & f )
{
f.a = 0;
}
};
如您所见,静态成员whatnot()
可以操作传递给它的类的任何实例的私有成员。毕竟,这是班上的一员。它没有任何保证不会更改任何特定的类实例。另一方面,const
成员保证其操作的实例不会被更改。
对于辅助函数,虽然不需要直接访问对象的内部,但更喜欢非成员非友情函数(http://www.gotw.ca/publications/c++cs.htm中的第44项)
答案 2 :(得分:-1)
静态方法的一大优点是,您不需要指向类的指针即可调用该方法。我已经回顾了一些复杂的代码,它们多次将指针作为参数传递,因此可以调用方法(可以是静态的)。如果适用于这种情况,使用静态方法可以简化代码并可能减少传递参数所需的寄存器数量。由于您只能使用其中一种,因此您应该选择最适合您的方法。