标签:
int b = 100; const int* a = &b; //情况1 int const* a = &b; //情况2 int* const a = &b; //情况3 const int* const a = &b; //情况4
const修饰有三种情况:
第一:const在“ * ”左边,则const用来修饰指针所指向的变量,即指针指向为常量,如情况1,情况2;
第二:const在“ * ”右边,则const用来修饰指针本身,即指针本身是常量,如情况3;
第三:const在“ * ”两边,则const既修饰指针本身也修饰指针所指变量,如情况4;
注意:const的相对位置只与“ * ”有关,和变量的类型声明没有位置关系,其次const修饰指针所指变量时可以不初始化,但const修饰指针本身时必须初始化。
输入参数采用“指针传递”,那么加const修饰可以防止意外的改动该指针指向的内存单元,起到保护作用,如StringCopy函数
//输入参数: strSrc 输出参数:strDest void StringCopy(char* strDest, const char* strSrc);
如果还想保护指针本身,则可以声明指针本身为常量,例如:
void OutputString(const char* const pStr);
如果参数用于输出,不论它是什么类型,也不论它采用“指针传递”还是“引用传递”,都不能加const修饰,即const只能修饰输入参数。另外如果如果输入参数采用“值传递”,由于函数将自动用实参的拷贝初始化形参,因此即使在函数内部修改了该参数,改变的也只是堆栈上的拷贝而不是实参,所以一般不需要const修饰。最好不要把void Func(const int x)改为void Func(const int &x)这样即达不到提高效率的目的有让人费解。因为基本数据类型的参数不存在构造、析构的过程,除基本类型参数为推荐使用“const &传递”。
如果给“指针传递”的函数返回值加const修饰符,那么返回值是一种契约性常量,不能被直接修改,并且该返回值只能被赋值给加const修饰的同类型指针(除非强制转换),例如:
const char* GetString(void); //函数声明 char* str = GetString(); //编译错误 const char* str = GetString(); //正确
如果函数返回值采用“值传递”的方式,在一般情况下由于函数会把返回值拷贝到外部的临时存储单元中,所以加const修饰是没有什么意义的。
class CTextBlock { public: ... std::size_t length() const; private: char* pText; std::size_t textLength; bool lengthIsValid; }; std::size_t CTextBlock::length() const { if(!lengthIsValid) { textLength = std::strlen(pText); //错误,const成员函数不能给类中的 lengthIsValid = true; //成员变量赋值 } return textlength; }
const成员函数不能给类中的成员变量赋值,如果非得给类中成员变量赋值,可以用mutable来修饰成员变量,如:
mutable std::size_t textLength; mutable bool lengthIsValid;
第一:const常量有数据类型,而宏常量没有数据类型。编译器可以对前者进行类型安全检查而对后者只能进行字符替换,没有安全类型检查,并且替换中可能会出现意料不到的错误(边际效应)。
第二:编译处理宏定义时,在预编译时将实际将所有宏定义全部替换成成实际值然后进行编译,const修饰的值在编译期间的常量,同时const常量可能比define产生更小的代码量。
第三:有些集成化调试工具可以对const常量进行调试,但不能对宏常量进行调试。
第四:#define不能创建一个class专属常量,也不能提供任何封装性,const可以定义class专属常量,如:
class GamePlayer { private: static const int NumTurns = 5; int scores[NumTurns]; }
建议:对于单纯常量,最好以const对象或enums替换#define;对应形似函数的宏,最好用inline函数替换#define。
补充知识:
C中的const是“一个不能被改变的普通变量”,它总是占用内存,而且它是全局变量,C编译器不能把const看成一个变异期间的常量,在C中下面的函数是不合理的
const bufsize = 100; char buf[bufsize];
而在C++中是正确的,C默认const是外部连接的,C++默认const是内部连接的
标签:
原文地址:http://www.cnblogs.com/hanyefeng/p/4704104.html