const和static的区别

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

const和static的区别

一、const关键字

如果把const放在变量类型名前,说明这个变量的值是保持不变的,该变量必须在定义时初始化,初始化后对它进行的任何赋值都是非法的。

当指针或者引用指向一个常量时,必须在类型名前使用const标识这个指针或者引用指向的“变量”为常量,没有的话就是语法错误。如:const int x=5; const int*px=&x;const int&rx=x;这样一来,直接修改x是不可能的,通过*px或者rx修改x也是不可能的。当然,这个指针还能指向其他的地方,因为指针本身并没有被标识为const的。比如,px=&y;

假如变量是一个非常量变量,而指针或者引用的类型名前使用了const,那么,可以直接修改变量,不能通过指针或者引用修改变量。

如果想让一个指针本身成为const的,就要在*后加const,即int*const p =&x;这个时候,p就不能再指向其他变量。假如x是非常量的,那它可以通过指针进行修改,因为x并没有标识为const。当然,引用天生就是const的,它必须被初始化,而且初始化后就不能再指向新的变量。比如,int x=5;int&r =x;r=y;第二句代码不会让r指向y,而是让x的值变成了y。

如果在函数接口(参数)中使用const,和在值、指针中使用是类似的。但是,这就更难让函数返回指向这个参数对象的指针或者引用了。如果允许的话,客户代码就有可能通过别名修改常量。比如,

class Point

{

int x,y;

public:

Point closestPointVal(const Point&pt)

{if(x*x+y*y

return*this;

else return pt;}

Point*closestPointPtr(const Point&pt)

{return(x*x+y*y

Point&closestPointRef(const Point&pt)

{return(x*x+y*y

第一个函数是返回值的,不管用不用const,都不会修改实参pt。而第二个函数可以返回指向pt实参的指针。客户代码就可以使用这个指针修改实际参数对象的状态。同样,第三个函数返回的引用也能修改实参对象的状态。假如这样的函数是合法的,那么就有可能误用,误用后如果出了错,很难弄清是这里出的错,所以编译程序直接就认为这样的函数不合法。也就是,参数对象使用了const,而返回类型没有,这是错误的。

C++提供了三种方法解决这个问题:1.参数不使用const;2.在成员函数内部,使用const_cast运算符移去const属性;3.在另外合适的地方添加const。一个真正的程序员是不会放过任何一个机会,将设计人员的设计意图传达给客户代码程序员和维护人员的。所以,假如某个参数没有被修改,就要用const 来明确说明。而使用const_cast也很糟糕,不易理解。所以只能使用第三种方法,在函数返回值前加上const,接收该返回值的指针或者引用也要是const 的。这样的话,返回值只能作为右值,不能作为左值。这样的返回值不能调用它所在类的成员函数。

C++提供const关键字,不是为了保证一个变量不被修改,而是为了方便编译程序和维护人员弄清楚一个实体在程序中是否被修改了。如果函数接口中声明参数为const,我们就认为这个参数不会改变,如果没有声明为const,就认为这个参数一定被改变了,而不管函数到底有没有改变这个参数。

其实,const还有一个含义,就是在函数的参数列表的“)”之后,函数体的“{”之前。这种用法说明函数不会修改目标对象的值。

二、静态类成员

每建立一个类对象实例,都会为该实例创建一个单独的数据成员集合。不管是将对象定义为有名的局部变量,有名的全局变量,或者使用new定义为未命名的动态变量,或者按值传递一个对象作为函数参数,或者从一个函数按值返回一个对象。而对于成员函数,它们的目标代码却只产生一次。因为每个程序函数都有一个隐含的参数,即this指针。

1用全局变量作为类特性

类为对象实例提供了一个蓝图或者说是模板,类的成员变量都是这个类的所有实例的共性,类的每一个实例都有一个单独的副本。但是有时我们需要为一个类的所有实例提供共有的数据成员副本,这比在每个类对象中维护单独的副本能更有效的合理利用内存。最常见的例子就是对类的实例进行计数。假如这个计数变量count被定义在类中,在构造函数中对其加1,在析构函数中对其减1,似乎能实现计数作用。但是实际上却是做不到的。因为count是类的成员变量,每个实例都有一个count,构造函数对其加1,只是对自己的count加了1。

使用全局变量就能解决这个问题。但是将它用在大型程序中,存在一些问题,这些问题在前面都讲过了。首先在客户代码任意地方都可能使用count,增加了模块之间的依赖性。其次,全局变量名增加了重名机会。最重要的是,count作为全局变量出现时,维护人员不能很好的了解它是做什么的,除非看注释或者查阅大量其他代码。

2static的含义

static和const一样很复杂。

首先,将static用于一个全局变量,是说明该全局变量只对定义在同一个文件中的函数可见。即使在另一个文件中使用了extern,另一个文件中的函数也不能访问这个全局变量。

static的第二个含义是用于一个函数前,说明该函数只能在同一个文件中调用。

第三个含义是static用于函数的局部变量。它表明该变量的值不会因为函数终止而消失,它会被保存下来。再次调用该函数时,这个保存下来的值会用来初始化该变量。

第四个含义就是用于类的成员变量。它表明对类的所有对象,这个数据成员都只有一个实例。这个实例被所有对象共有。static的成员变量可以是private、public、protected的。定义和访问的语法也和其他数据成员一样。

3静态数据成员的初始化

相关文档
最新文档