const正确让我有点困惑。
你用什么经验法则决定什么时候应该是const?
e.g。考虑这个例子
class MyClass
{
string ToString(); // this one?
const string& ToString(); // or this?
const string& ToString() const; // or this?
char* ToString(); // What about this?
const char* ToString(); // or this?
const char* ToString() const; // or this?
const char const* ToString(); // Is this legal?
const char const* ToString() const; // how about this?
char const* ToString(); // or even this?
};
Const会让人感到困惑。
所有这些ToString方法之间有什么区别?
如果我理解正确,第一个返回一个可以修改的新字符串对象 如果需要的话。 第二个返回一个常量引用,也许它应该是字符串const& toString()方法。 第三个可能是废话,因为引用总是不变的是正确的吗?
以为我会在那里抛出旧的char *版本进行比较,因为我有返回对象指针的方法,我不确定它们是否应该是const。
我想我只是想了解const正确性的局限性和好处,以及如何预先确定某些东西是否为const以及如何正确应用const,因为将const放在不同的位置会改变含义。
编辑:同样,我如何处理'...丢弃限定词'。这究竟意味着什么?答案 0 :(得分:2)
使用const
的位置取决于函数的用途。正如詹姆斯在评论中提出的那样(值得作为答案),将const
放在任何地方:
如果该函数旨在修改其对象实例中的状态,不将const
放在签名的末尾。
如果该函数旨在修改其中一个参考或指针参数,不将const
放在参数上。
如果应修改指针或引用引用的变量,不将const
放在类型上(请记住,const
紧接在之前适用于定义的部分。
如果返回的引用/指针引用了不应被接收的变量,执行将const
放在类型上。
在不知道函数的目的的情况下,回答问题中给出的示例是不可能的。我倾向于使用string ToString() const
和char* ToString() const
,以及关于谁负责delete
char*
的明确文档。
作为额外注释,const char*
和char const*
是相同的(指向不可修改字符的指针)。另一方面,char* const
是指向可修改字符的不可修改的指针。
答案 1 :(得分:1)
我总是将这些常见问题用作这些类型的问题作为起点。 http://www.parashift.com/c++-faq-lite/const-correctness.html
答案 2 :(得分:0)
您不能重载具有相同名称和相同参数但返回类型不同的函数。你可能知道这一点,但只是确定。
const
括号后的 ()
表示该函数不会更改您调用它的对象。通常称为ToString
的东西不会改变对象,所以在所有情况下你可能都需要一个const方法。
返回string
和返回const string&
之间的区别在于引用不会进行对象复制并且可能更快,但只有在您已经拥有{{1}时才能执行此操作} object(例如,作为string
的私有成员)。如果不是(比如你需要将几个数据分块然后返回该字符串),你需要按值返回MyClass
。
使用string
对象通常比使用C风格的string
指针更受欢迎,但是因为你问:第四个char*
,会让其他代码更改返回的字符字符串,这可能是一件坏事。 char*
,const char*
和char const*
都是一样的。 const char const*
在技术上是不同的,但由于返回char *const
无关紧要的原因,返回类型不会很多:调用者可以只复制然后更改返回值。
简而言之,最好的形式是:
const int
答案 3 :(得分:0)
问题的一些变化是返回string
与char *
。我认为这与const
讨论无关(如果不是,请告诉我);我正在考虑string
回复变化。
class MyClass
{
string ToString(); // A
string & ToString(); // B (I added this)
const string& ToString(); // C
const string& ToString() const; // D
};
我的偏好按此顺序排列:D,C,B,A。
在所有变体中,const
以两种方式使用:
返回类型说明符[D]中的第一个const
这意味着返回的对象不能用于修改返回的对象。这句话听起来很有趣,不是吗?好吧,可能还有其他修改对象的方法,而const
无法阻止它。请参阅此FAQ item。
类不变[D]中的第二个const
这意味着该方法不会改变(修改)类对象。
我更喜欢D而不是其他任何因为D保证不会修改调用该方法的对象。如果可以在不修改对象的情况下实现目标(即可以实现方法),那么在设计方面就是一个巨大的胜利。我尽可能地使用它。 但是如果必须修改对象 (即,如果不修改对象就无法实现该方法),则排除D。
其余的B和C都优于A,因为B和C返回引用,这避免了A中所需的复制构造。
在B和C之间,C是优选的,因为它返回const
引用。
答案 4 :(得分:-1)
我发现this是一个有用的指南
答案 5 :(得分:-1)
你用什么经验法则决定什么时候应该是const?
随时随地使用它。然后,当您需要修改对象或授予对可能修改对象的内容的访问权限(即将引用或代理返回到内部状态)时,不使用它。
第三个可能是胡说八道,因为引用总是不变的是正确的吗?
不,这不正确。引用是别名,而不是变量。因此,您无法更改引用“指向”哪个变量,就像使用指针一样。但是,您可能引用了一个可变对象(std::string&
)。
所有这些ToString方法之间有什么区别?
他们在内存管理技术方面差异很大,但从高层次来看,他们都做同样的事情,除了以下内容:
char* ToString();
该ont返回指向可变字符数组的指针(可能是内部状态)。
请注意以下系列:
char const* ToString();
const char* ToString(); // or this?
const char const* ToString(); // Is this legal?
是写同一件事的不同方法。无论你是否写入,本机类型都是按值返回的const。
以下2是C ++中返回字符串的首选方式(在最后提供了额外的const
):
string ToString(); // this one?
const string& ToString(); // or this?
您将使用哪两个取决于您从哪里获得价值。如果字符串是数据成员,我建议你选择后者,因为它通常更快,但如果你的字符串实现使用Copy-On-Write语义则不是很多。如果你必须计算一个值并返回它,你必须使用前者,因为你不能返回对局部变量的引用。
以下两项都是正确的,但我仍然建议您使用std::string
const char* ToString() const; // or this?
const char const* ToString() const; // how about this?