[英]Pointer vs. Reference
在给函数提供原始变量时,最好的做法是:
unsigned long x = 4;
void func1(unsigned long& val) {
val = 5;
}
func1(x);
要么:
void func2(unsigned long* val) {
*val = 5;
}
func2(&x);
IOW:有没有理由选择一个而不是另一个?
我的经验法则是:
如果你想用它们做指针运算(例如递增指针地址以逐步遍历数组)或者你必须传递一个NULL指针,请使用指针。
否则使用参考。
我真的认为你将从建立以下函数调用编码指南中受益:
正如其他所有地方,永远是const
-correct。
const
说明符。 如果值0 / NULL是当前上下文中的有效输入,则仅通过指针传递值。
理由1:作为调用者 ,您会看到无论您传入的是什么,都必须处于可用状态。
理由2:由于叫 ,你知道,无论发生什么事在处于可用状态。 因此,不需要对该值进行NULL检查或错误处理。
基本原理3:基础知识1和2将被编译器强制执行 。 如果可以的话,总是在编译时捕获错误。
如果函数参数是out-value,则通过引用传递它。
只有当值是POD( 普通旧数据结构 )或足够小(内存方式)或以其他方式足够便宜(按时间)复制时,选择“按值传递”而不是“传递const引用”。
这最终成为主观的。 到目前为止的讨论很有用,但我认为没有正确或果断的答案。 很多将取决于风格指南和您当时的需求。
虽然使用指针有一些不同的功能(无论是否可以为NULL),但输出参数的最大实际差异纯粹是语法。 例如,谷歌的C ++风格指南( https://google.github.io/styleguide/cppguide.html#Reference_Arguments )只强制指针输出参数,并且只允许引用为const。 推理是可读性:具有值语法的东西不应该具有指针语义。 我并不是说这必然是对或错,但我认为这里的重点是风格,而不是正确性。
如果要修改变量的值,则应传递指针。 即使技术上传递引用或指针是相同的,在您的用例中传递指针更具可读性,因为它“通告”该值将由函数更改的事实。
如果您有一个参数,您可能需要指示缺少值,通常的做法是使参数成为指针值并传入NULL。
在大多数情况下(从安全角度来看)更好的解决方案是使用boost :: optional 。 这允许您通过引用传递可选值,也可以作为返回值。
// Sample method using optional as input parameter
void PrintOptional(const boost::optional<std::string>& optional_str)
{
if (optional_str)
{
cout << *optional_str << std::endl;
}
else
{
cout << "(no string)" << std::endl;
}
}
// Sample method using optional as return value
boost::optional<int> ReturnOptional(bool return_nothing)
{
if (return_nothing)
{
return boost::optional<int>();
}
return boost::optional<int>(42);
}
指针
当前未指向有效内存位置的指针的值为null(为零)
BaseType* ptrBaseType; BaseType objBaseType; ptrBaseType = &objBaseType;
&是一个一元运算符,返回其操作数的内存地址。
解除引用运算符(*)用于访问存储在指针指向的变量中的值。
int nVar = 7; int* ptrVar = &nVar; int nVar2 = *ptrVar;
参考
引用(&)类似于现有变量的别名。
引用(&)就像一个自动解除引用的常量指针。
它通常用于函数参数列表和函数返回值。
必须在创建引用时初始化引用。
将引用初始化为对象后,无法将其更改为引用另一个对象。
您不能有NULL引用。
const引用可以引用const int。 它由一个带有const值的临时变量完成
int i = 3; //integer declaration int * pi = &i; //pi points to the integer i int& ri = i; //ri is refers to integer i – creation of reference and initialization
尽可能使用引用,必要时使用指针。 从C ++ FAQ:“我应该何时使用引用,何时应该使用指针?”
引用是隐式指针。 基本上,您可以更改引用指向的值,但不能将引用更改为指向其他内容。 所以我的2美分是,如果您只想更改参数的值,则将其作为参考传递,但如果您需要将参数更改为指向其他对象,请使用指针传递它。
考虑一下C#的out关键字。 编译器要求方法的调用者将out关键字应用于任何out args,即使它已经知道它们是否存在。 这旨在增强可读性。 虽然使用现代IDE,我倾向于认为这是语法(或语义)突出显示的工作。
除非您有理由更改/保留您传入的内容,否则请通过const引用。
在大多数情况下,这将是最有效的方法。
确保在每个不希望更改的参数上使用const,因为这不仅可以保护您不会在函数中做一些愚蠢的事情,而且可以很好地向其他用户指示函数对传入的值的作用。 这包括当你只想改变指向的时候制作指针const ...
指针:
nullptr
(或NULL
)。 &
,明确表示您正在修改对象。 参考文献:
&
。 这有时被认为是错误的,因为您必须转到函数的实现以查看您的参数是否被修改。 引用类似于指针,除了您不需要使用前缀*来访问引用引用的值。 此外,不能在初始化之后引用不同的对象。
引用对于指定函数参数特别有用。
有关更多信息,请参阅“Bjarne Stroustrup”(2014)第11-12页的“C ++之旅”
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.