# 引用与函数参数

URL: https://caijiao.org/cpp/function/ref-params
Source: docs/cpp/function/ref-params.md
Description: 本节将讨论如何使用引用作为函数参数，了解引用传递的优势以及如何使用引用优化函数调用。

在 C++ 中，函数参数传递有两种主要方式：**值传递** 和 **引用传递**。引用传递允许函数直接操作传入的变量，而无需拷贝变量的值。这种方式常用于提高效率，尤其是对于大对象或复杂数据类型。

## 引用作为函数参数

当函数的参数通过引用传递时，实际上是传递了该参数的别名。函数可以修改引用参数的值，修改会影响调用该函数的原始变量。这种方式的主要优点是减少了拷贝的开销，并且能够直接修改外部变量。

### 示例：通过引用传递参数

```cpp
#include <iostream>
using namespace std;

void increment(int& num) {
    num++;  // 修改传入的变量
}

int main() {
    int a = 5;
    increment(a);  // 传递 a 的引用
    cout << "a 的值: " << a << endl;  // 输出修改后的 a 的值

    return 0;
}
````

### 输出：

```
a 的值: 6
```

在这个例子中，`increment` 函数接收 `a` 的引用作为参数。由于传递的是引用，`increment` 函数对 `num` 的修改直接影响了 `a` 的值。

## 引用传递的优点

1. **避免不必要的拷贝**：如果参数是一个大的数据结构，使用引用可以避免拷贝整个对象，从而提高效率。
2. **修改调用者的参数**：引用传递允许函数修改外部变量的值。这是通过值传递无法做到的。
3. **提高效率**：对于大数据结构（如大数组或对象），引用传递比值传递节省了内存和时间开销。

## 常量引用

有时你希望传递参数时避免修改其值，同时又希望避免拷贝。此时，可以使用 **常量引用**（`const` 引用）。常量引用使得参数无法在函数内部被修改，同时避免了大对象的拷贝。

### 示例：常量引用

```cpp
#include <iostream>
using namespace std;

void printValue(const int& num) {
    cout << "传入的值: " << num << endl;  // 不能修改 num
}

int main() {
    int a = 10;
    printValue(a);  // 传递 a 的常量引用

    return 0;
}
```

### 输出：

```
传入的值: 10
```

在上述代码中，`num` 是常量引用，确保了在 `printValue` 函数中无法修改 `num` 的值。常量引用特别适用于需要传递大型对象但又不想修改其值的场景。

## 引用与指针作为参数的比较

* **引用**：引用不需要显式解引用操作（不像指针），语法更简洁。引用总是绑定到某个对象，无法为 `nullptr`。
* **指针**：指针允许为 `nullptr`，并且需要解引用才能访问目标值。指针的使用较为灵活，但也更容易出错。

## 小结

* **引用传递** 是 C++ 中提高函数效率和避免不必要拷贝的重要手段。
* 使用引用作为函数参数时，函数可以修改传入的变量。
* **常量引用** 是优化性能且保护数据不被修改的有效方式。
* 引用传递比指针传递更简洁、更安全，适用于大多数场景。

理解引用传递的优点和应用场景，可以帮助你编写更高效、易于维护的 C++ 代码。
