C++12.6 static 数据成员、static成员函数
2015-06-23 19:55
337 查看
##简介
通常,非static数据成员存在于类类型的每个对象中。不像普通的数据成员,static数据成员独立于该类的任意对象而存在:每个static数据成员是与类关联的对象,并不与该类的对象相关联的。
static函数没有this指针
static成员函数是类的组成部分但不是任何对象的组成部分,因此,static成员函数没有this指针,通过使用非static成员显示或隐式地地引用this是一个编译时错误。
因为static成员不是任何对象的组成部分,所以static成员函数不能声明为const.毕竟,将成员函数声明为const就是承若不会修改该函数所属的对象。最后,static成员函数也不能声明为虚函数(15.2.4)。
可以通过作用域操作符从类直接调用static成员,或者通过对象、引用或指向该类类型对象的指针间接调用。
非const static成员的初始化必须 在类体外进行。
====================================================================================
然而,全局对象会破坏封装:对象需要支持特定类抽象的实现。如果对象是全局的,一般的用户代码就可以修改这个值。类可以定义类静态成员,而不是定义一个可普遍访问的全局对象。
通常,非static数据成员存在于类类型的每个对象中。不像普通的数据成员,static数据成员独立于该类的任意对象而存在:每个static数据成员是与类关联的对象,并不与该类的对象相关联的。
类可以定义共享的static数据成员,类也可以定义static成员函数。static成员函数没有this形参,它可以直接访问所属类的static成员,但不能直接使用非static成员。
可以实施封装。static成员可以是私有成员,而全局对象不可以;
通过阅读程序容器看出static成员是与特定类关联的。
像其他成员一样,类成员函数可以不用作用域操作符来引用类的static成员:
static函数没有this指针
static成员函数是类的组成部分但不是任何对象的组成部分,因此,static成员函数没有this指针,通过使用非static成员显示或隐式地地引用this是一个编译时错误。
因为static成员不是任何对象的组成部分,所以static成员函数不能声明为const.毕竟,将成员函数声明为const就是承若不会修改该函数所属的对象。最后,static成员函数也不能声明为虚函数(15.2.4)。
static数据成员必须在类定义体的外部定义(正好一次)。不像普通数据成员,static数据成员不是通过类构造函数进行初始化,而是应该在定义时进行初始化。
保证对象正好定义一次的最好办法,就是将static数据成员的定义放在包含类的非内联成员函数定义的文件中。
定义static数据成员的方式与定义其他类成员和变量的方式相同:先指定类型名,接着是成员的完全限定名。
像使用任意的类成员一样,在类定义体外部引用类的static成员时,必须指定成员是在哪个类中定义的。然而,static关键字只能用于类定义体内部的声明中,定义不能标为static
例外,只要初始化式是一个常量表达式,整型const static数据成员就可以在类的定义体中进行初始化:
const static数据成员在类的定义体中初始化时,该数据成员仍然必须在类的定义体之外进行定义。
在类内部提供成员初始化式后,成员的定义不必再指定初始值。
static数据成员也可以是该成员所属的类类型。非static成员被限定声明为其自身类对象的指针或引用:
p375: 在声明之后,定义之前,类Screen是一个不完全类型,即已知Screen是一个类型,但不知道里面有哪些成员。如果类类型是不完全类型,那么数据成员只能是指向该类类型的指针或引用。
因为只有当类定义体完成后才能定义类,因此类不能具有自身类型的数据成员,然而只要类名一出现就可以认为该类已经声明,此时,类的数据成员可以是指向自身的类型的指针或引用、
非static数据成员不能用做默认实参,因为它的值不能独立于所属的对象而使用,使用非static数据成员做默认实参,将无法提供对象以获取该成员的值。错误!!!
通常,非static数据成员存在于类类型的每个对象中。不像普通的数据成员,static数据成员独立于该类的任意对象而存在:每个static数据成员是与类关联的对象,并不与该类的对象相关联的。
static函数没有this指针
static成员函数是类的组成部分但不是任何对象的组成部分,因此,static成员函数没有this指针,通过使用非static成员显示或隐式地地引用this是一个编译时错误。
因为static成员不是任何对象的组成部分,所以static成员函数不能声明为const.毕竟,将成员函数声明为const就是承若不会修改该函数所属的对象。最后,static成员函数也不能声明为虚函数(15.2.4)。
可以通过作用域操作符从类直接调用static成员,或者通过对象、引用或指向该类类型对象的指针间接调用。
非const static成员的初始化必须 在类体外进行。
====================================================================================
一、static 类成员
对于特定类类型的全体对象而言,访问一个全局对象有时是有必要的,也许,在程序的任意点需要统计已经建设的特定类类型对象的数量;或者,全局对象可能是指向类的错误处理例程的一个指针。或者,它是指向类类型对象的内存自由存储区的一个指针。然而,全局对象会破坏封装:对象需要支持特定类抽象的实现。如果对象是全局的,一般的用户代码就可以修改这个值。类可以定义类静态成员,而不是定义一个可普遍访问的全局对象。
通常,非static数据成员存在于类类型的每个对象中。不像普通的数据成员,static数据成员独立于该类的任意对象而存在:每个static数据成员是与类关联的对象,并不与该类的对象相关联的。
类可以定义共享的static数据成员,类也可以定义static成员函数。static成员函数没有this形参,它可以直接访问所属类的static成员,但不能直接使用非static成员。
1、使用类的static成员而不是全局对象的优点:
static成员的名字是在类的作用域中,因此可以避免与其他类的成员或全局对象名字冲突;可以实施封装。static成员可以是私有成员,而全局对象不可以;
通过阅读程序容器看出static成员是与特定类关联的。
2、定义static成员
class Account{ public: void applyint(){amount +=amount*interestRate;} static double rate(){return interestRate; } static void rate(double);//声明一个static的成员函数 private: std::string owner; double amount; //类的每个对象具有两个数据成员:owner和amount。对象没有与static数据成员对应的数据成员,但是,存在一个单独的interestRate对象,由Account类型的全体对象共享。 static double interestRate; static double initRate(); };
3、使用类的static成员—-类操作符、对象、引用或指向该类类型对象的指针
可以通过作用域操作符从类直接调用static成员,或者通过对象、引用或指向该类类型对象的指针间接调用。Account ac1; Account *ac2=&ac1; double rate; rate =ac1.rate(); rate =ac2->rate(); rate =Account::rate();
像其他成员一样,类成员函数可以不用作用域操作符来引用类的static成员:
class Account{ public: void applyint(){amount+=amount*interestRate;} };
二、static成员函数
Account类有两个名为rate的static成员函数,其中一个定义在类的内部。当我们在类的外部定义static成员时,无须重复指定static保留字,该保留字只出现在类定义体内部的声明处:static函数没有this指针
static成员函数是类的组成部分但不是任何对象的组成部分,因此,static成员函数没有this指针,通过使用非static成员显示或隐式地地引用this是一个编译时错误。
因为static成员不是任何对象的组成部分,所以static成员函数不能声明为const.毕竟,将成员函数声明为const就是承若不会修改该函数所属的对象。最后,static成员函数也不能声明为虚函数(15.2.4)。
void Account::rate(double newRate)//在类外定义的static成员函数,只需要写类作用域,不需要写static了。 { interestRate = newRate; }
3、static数据成员
static数据成员可以声明为任意类型,可以是常量、引用、数组、类类型,等等。static数据成员必须在类定义体的外部定义(正好一次)。不像普通数据成员,static数据成员不是通过类构造函数进行初始化,而是应该在定义时进行初始化。
保证对象正好定义一次的最好办法,就是将static数据成员的定义放在包含类的非内联成员函数定义的文件中。
定义static数据成员的方式与定义其他类成员和变量的方式相同:先指定类型名,接着是成员的完全限定名。
//可以定义如下interestRate double Account::interestRate = initRate(); //定义名为interestRate的static对象,它是类Account的成员,为double类型。像其他成员一样,一旦成员名出现,static成员的定义就是在类作用域中。因此,我们可以没有限定地直接使用名为initRate的static成员函数,作为interestRate的初始化式。注意,尽管initRate是私有的,我们仍然可以使用该函数来初始化interestRate。像任意的其他成员定义一样,interestRate的定义是在类的作用域中,因此可以访问该类的私有成员。
像使用任意的类成员一样,在类定义体外部引用类的static成员时,必须指定成员是在哪个类中定义的。然而,static关键字只能用于类定义体内部的声明中,定义不能标为static
1、特殊的整型const static成员
类的static成员,像普通数据成员一样,不能在类的定义体中初始化。相反,const类型的static数据成员通常在定义时初始化。例外,只要初始化式是一个常量表达式,整型const static数据成员就可以在类的定义体中进行初始化:
class Account{ public: static double rate(){return interestRate; } static void rate(double);//声明一个static的成员函数 private: static const int period=30;//用常量表达式初始化一个static const类型的变量 double daily_tbl[period]; };
const static数据成员在类的定义体中初始化时,该数据成员仍然必须在类的定义体之外进行定义。
在类内部提供成员初始化式后,成员的定义不必再指定初始值。
const int Account::period;
2、static成员不是类对象的组成部分
static数据成员独立于任何对象。static数据成员也可以是该成员所属的类类型。非static成员被限定声明为其自身类对象的指针或引用:
p375: 在声明之后,定义之前,类Screen是一个不完全类型,即已知Screen是一个类型,但不知道里面有哪些成员。如果类类型是不完全类型,那么数据成员只能是指向该类类型的指针或引用。
因为只有当类定义体完成后才能定义类,因此类不能具有自身类型的数据成员,然而只要类名一出现就可以认为该类已经声明,此时,类的数据成员可以是指向自身的类型的指针或引用、
class Bar{ public: private: static Bar mem1;//ok Bar *mem2;//ok Bar mem3;//no!!!!因为Bar是一个不完全类型,所以只能定义它的非static的指针或引用。 };
//static数据成员可以用作默认实参 class Screen{ public: Screen& clear(char = bkground);//static成员做默认实参 private: static const char bkground = '#'; };
非static数据成员不能用做默认实参,因为它的值不能独立于所属的对象而使用,使用非static数据成员做默认实参,将无法提供对象以获取该成员的值。错误!!!
相关文章推荐
- 约瑟夫环的C语言和86/88汇编非递归算法
- C++内存管理
- C++算法之——常用算法总结
- C++ const用法
- Visual C++ Tips: error C2823: a typedef template is illegal
- C++十进制转二级制
- 第16周《C++语言基础》实践参考——有些数的阶乘不算了
- 第16周《C++语言基础》实践参考——平方根中的异常
- 八数码问题:C++广度搜索实现
- [C++设计模式] singleton 单例模式
- 探索C/C++大数快(自然数)模板
- [LeetCode] Search a 2D Matrix
- C++中的namespace
- C/C++中移位实现乘除法运算
- VC++获取操作系统的版本 GetVersionEx函数
- 学习C语言,困难吗?
- c++ container with user defined compare function
- 学习C语言,困难吗?
- 学习C语言,困难吗?
- "stdafx.cpp"编译引起的C2859、C1083、LNK2001错误