按指针传递和按引用传递

50

可能是重复问题:
C++中指针变量和引用变量的区别是什么?
在C++中,通过指针传递参数与通过引用传递参数相比有哪些优势?

在这两种情况下,我都达到了结果。 那么什么时候应该使用其中一种?我们使用其中一种的原因是什么?

#include <iostream>
using namespace std;
void swap(int* x, int* y)
{
    int z = *x;
    *x=*y;
    *y=z;
}
void swap(int& x, int& y)
{
    int z = x;
    x=y;
    y=z;
}

int main()
{
    int a = 45;
    int b = 35;
    cout<<"Before Swap\n";
    cout<<"a="<<a<<" b="<<b<<"\n";

    swap(&a,&b);
    cout<<"After Swap with pass by pointer\n";
    cout<<"a="<<a<<" b="<<b<<"\n";

    swap(a,b);
    cout<<"After Swap with pass by reference\n";
    cout<<"a="<<a<<" b="<<b<<"\n";
}

输出

Before Swap
a=45 b=35
After Swap with pass by pointer
a=35 b=45

After Swap with pass by reference
a=45 b=35

https://dev59.com/OHVD5IYBdhLWcg3wBm1g - Tae-Sung Shin
在C++中,通过指针传递和通过引用传递有哪些好处? - cpx
5个回答

29
参考文献在语义上如下所示:
T& <=> *(T * const)
const T& <=> *(T const * const)
T&& <=> [无 C 相关] (C++11)
与其他答案一样,以下来自 C++ FAQ 的简短回答:尽可能使用引用,需要时使用指针。
相比指针,一个优点是,在传递 NULL 时需要显式转换。但这仍然是可能的。在我测试过的编译器中,对于以下内容,没有任何编译器发出警告:
int* p() {
    return 0;
}
void x(int& y) {
  y = 1;
}
int main() {
   x(*p());
}

1
引用并不限制引用对象必须指向有效的内容。例如,你可以返回一个指向本地变量的引用。 - Seth Carnegie
1
如果您取消引用空指针,则可能会获得无效引用,因此在调用代码中仍需要小心。请参见https://dev59.com/VHVD5IYBdhLWcg3wL4mM#57656。 - Mark Ransom
1
这是可能的,但除非您正在取消引用未经检查的指针,否则不应该发生。如果您在取消引用指针之前不检查它们,那么我有一个消息告诉您... - moshbear
使用gcc 4.9.2版本,我得到如下错误:a.cpp:8:8: 错误:不能从类型为'int* (*)()'的rvalue初始化非const引用类型'int&'。 - Ondřej Čertík
@moshbear,现在它能正常运行了,谢谢! - Ondřej Čertík
显示剩余5条评论

6
实际上,大多数编译器对于这两个函数调用都会发出相同的代码,因为引用通常是使用指针实现的。
按照这种逻辑,在函数体中使用非const类型的引用参数时,生成的代码将仅在参数的地址上操作,并对其进行解引用。此外,当遇到对这样一个函数的调用时,编译器将生成传递参数地址而不是复制它们值的代码。
基本上,从实现角度讲,引用和指针并没有太大的区别,主要(也非常重要)的区别在于哲学上:引用是对象本身,只是名字不同。
与指针相比,引用还有一些优点(例如,它们不能为NULL,因此使用起来更安全)。因此,如果可以使用C++,则通常认为通过引用传递更加优雅,也应该被优先考虑。但是,在C中不存在按引用传递,因此如果你想编写C代码(或者说骇人听闻地,编写既能够使用C编译器又能够使用C++编译器的代码,尽管这不是一个好主意),那么你就必须限制自己使用指针。

4
通过指针传递是在C语言中实现“按引用传递”的唯一方式,因此它仍然被广泛使用。
如果要表示参数未使用或无效,请使用NULL指针作为一个方便的约定,所以在这种情况下使用指针。
引用一旦设置就无法更新,因此如果需要重新分配,则应使用指针。
在没有充分理由的情况下,请优先使用引用。如果可能,请将其设为const

4

这里有一篇关于此事的好文章 - "尽可能使用引用,必须使用指针。"


2

在需要引用时始终使用引用,只有在需要引用无法引用的NULL时才使用指针。

请参阅本FAQ


int& x = *static_cast<int*>(NULL); - moshbear

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接