我总是搞砸如何正确使用const int*、const int*const和int const*。有没有一套规则来定义你能做什么和不能做什么?

我想知道在赋值、传递给函数等方面的所有注意事项。


当前回答

要简单地记住:

若const在*之前,则值为常量。

如果const在*之后,则地址为常量。

如果const在*之前和之后都可用,则值和地址都是常量。

e.g.

int*常量变量//这里地址是恒定的。int常量*var//这里的值是恒定的。int常量*常量变量;//值和地址都是常量。

其他回答

C++中围绕常量正确性还有许多其他微妙之处。我想这里的问题只是关于C,但我会给出一些相关的例子,因为标记是C++:

通常将字符串等大参数作为TYPE const&传递,这会防止对象被修改或复制。例子:TYPE&TYPE::operator=(const TYPE&rhs){…return*this;}但是TYPE&const是没有意义的,因为引用总是常量。您应该始终将不修改类的类方法标记为const,否则不能从TYPE const引用调用该方法。例子:bool TYPE::运算符==(const TYPE&rhs)const{…}在一些常见情况下,返回值和方法都应该是常量。例子:const TYPE TYPE::运算符+(const TYPE&rhs)const{…}事实上,const方法不能返回内部类数据作为对非常量的引用。因此,必须经常使用常量重载创建常量和非常量方法。例如,如果定义T const&operator[](unsigned i)const;,那么您可能还需要以下给出的非常量版本:内联T运算符[](无符号i)(&O){返回const_cast<char&>(static_cast<const TYPE&>(*this)[](i));}

事实上,C中没有常量函数,非成员函数本身在C++中不能是常量,常量方法可能有副作用,编译器不能使用常量函数来避免重复的函数调用。事实上,即使是一个简单的int const&reference,它引用的值也可能在其他地方更改。

对我来说,常量的位置,即它相对于*是出现在左侧还是右侧,还是同时出现在左侧和右侧,有助于我理解实际含义。

*左边的常量表示指针指向的对象是常量对象。*右边的常量表示指针是常量指针。

下表摘自斯坦福CS106L标准C++编程实验室课程阅读器。

我在下面画了一张图片来解释这一点,也许会有所帮助。

int const v和const int v是相同的。

一般规则是const关键字应用于它前面的内容。异常,起始常量适用于以下内容。

constint*与intconst*相同,表示“指向常量int的指针”。const int*const与int const*const相同,表示“指向常量int的常量指针”。

编辑:对于该做的和不该做的,如果这个答案还不够,你能更准确地说出你想要什么吗?

反向阅读(由顺时针/螺旋法则驱动):

int*-指向int的指针int const*-指向const int的指针int*const-指向int的const指针int const*const-指向const int的const指针

现在,第一个常量可以位于类型的任一侧,因此:

常量int*==int常量*const int*const==int const*const

如果你想变得疯狂,你可以这样做:

int**-指向int指针的指针int**const-指向int指针的const指针int*const*-指向int的const指针int const**-指向常量int的指针int*const*const-指向int的常量指针的常量指针...

为了确保我们清楚const的含义:

int a = 5, b = 10, c = 15;

const int* foo;     // pointer to constant int.
foo = &a;           // assignment to where foo points to.

/* dummy statement*/
*foo = 6;           // the value of a can´t get changed through the pointer.

foo = &b;           // the pointer foo can be changed.



int *const bar = &c;  // constant pointer to int 
                      // note, you actually need to set the pointer 
                      // here because you can't change it later ;)

*bar = 16;            // the value of c can be changed through the pointer.    

/* dummy statement*/
bar = &a;             // not possible because bar is a constant pointer.           

foo是指向常量整数的变量指针。这允许您更改指向的内容,但不更改指向的值。最常见的情况是,C样式字符串中有一个指向常量字符的指针。您可以更改指向的字符串,但不能更改这些字符串的内容。当字符串本身位于程序的数据段中且不应更改时,这一点很重要。

bar是指向可更改值的常量或固定指针。这就像没有额外语法糖的引用。由于这一事实,通常您会在使用T*常量指针的地方使用引用,除非您需要允许NULL指针。