7.1 函数基础
7.1.1 为什么需要函数?
函数是C++程序的基本构建块,使用函数的好处:
- 代码复用:相同逻辑只写一次,多处调用
- 模块化:将复杂问题分解为小的、可管理的部分
- 可维护性:修改一处,全局生效
- 可读性:函数名本身就是文档
7.1.2 函数的三要素
① 函数原型(声明):告诉编译器函数的接口
② 函数定义:实现函数的具体逻辑
③ 函数调用:使用函数
cpp
// function_basics.cpp -- 函数三要素示例
#include <iostream>
// ① 函数原型(声明):在main()之前声明
// 格式:返回类型 函数名(参数类型列表);
double square(double x); // 求平方
void printLine(int n); // 打印分隔线
int add(int a, int b); // 求和
int main()
{
using namespace std;
// ③ 函数调用
double result = square(5.0);
cout << "5的平方 = " << result << endl;
printLine(20);
cout << "3 + 4 = " << add(3, 4) << endl;
return 0;
}
// ② 函数定义:实现具体逻辑
double square(double x)
{
return x * x;
}
void printLine(int n)
{
for (int i = 0; i < n; i++)
std::cout << '-';
std::cout << std::endl;
}
int add(int a, int b)
{
return a + b;
}
输出:
5的平方 = 25
--------------------
3 + 4 = 7
7.1.3 函数原型的作用
cpp
// 函数原型让编译器能够:
// 1. 检查参数数量是否正确
// 2. 检查参数类型是否匹配(必要时自动转换)
// 3. 检查返回值类型
double cube(double x); // 原型
int main()
{
// 编译器根据原型检查调用是否正确
double v1 = cube(3.0); // ✅ 正确
double v2 = cube(3); // ✅ int自动转换为double
// double v3 = cube(3.0, 2.0); // ❌ 参数数量错误,编译报错
return 0;
}
double cube(double x) { return x * x * x; }
7.2 函数参数与返回值
7.2.1 按值传递(Pass by Value)
按值传递 :函数接收的是实参的副本,函数内部修改不影响原变量。
cpp
// pass_by_value.cpp -- 按值传递示例
#include <iostream>
// 尝试交换两个变量(按值传递,无效!)
void swap_wrong(int a, int b)
{
int temp = a;
a = b;
b = temp;
// a和b是副本,修改不影响原变量
std::cout << "函数内:a=" << a << " b=" << b << std::endl;
}
// 计算阶乘(按值传递,正确使用)
int factorial(int n)
{
int result = 1;
for (int i = 2; i <= n; i++)
result *= i;
return result;
}
int main()
{
using namespace std;
int x = 10, y = 20;
cout << "交换前:x=" << x << " y=" << y << endl;
swap_wrong(x, y);
cout << "交换后:x=" << x << " y=" << y << endl;
// x和y没有改变!
cout << "\n5! = " << factorial(5) << endl; // 120
cout << "10! = " << factorial(10) << endl; // 3628800
return 0;
}
输出:
交换前:x=10 y=20
函数内:a=20 b=10
交换后:x=10 y=20 ← 原变量未改变!
7.2.2 多个参数与返回值
cpp
// multi_params.cpp -- 多参数函数示例
#include <iostream>
#include <cmath>
// 计算两点之间的距离
double distance(double x1, double y1, double x2, double y2)
{
double dx = x2 - x1;
double dy = y2 - y1;
return sqrt(dx * dx + dy * dy);
}
// 判断是否为闰年
bool isLeapYear(int year)
{
return (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0);
}
// 返回两数中的较大值
int maxOf(int a, int b)
{
return (a > b) ? a : b;
}
int main()
{
using namespace std;
cout << "两点距离:" << distance(0, 0, 3, 4) << endl; // 5
cout << boolalpha;
cout << "2024年是闰年:" << isLeapYear(2024) << endl; // true
cout << "2023年是闰年:" << isLeapYear(2023) << endl; // false
cout << "max(15, 28) = " << maxOf(15, 28) << endl; // 28
return 0;
}
7.3 函数与数组
7.3.1 将数组传递给函数
数组名本质是指针,传递数组时传递的是首元素的地址,不是数组的副本。因此函数内修改数组会影响原数组。
cpp
// array_func.cpp -- 数组作为函数参数
#include <iostream>
// 方式1:int arr[](等价于 int* arr)
// 必须同时传入数组大小!
double average(int arr[], int size)
{
double sum = 0;
for (int i = 0; i < size; i++)
sum += arr[i];
return sum / size;
}
// 方式2:int* arr(与方式1完全等价)
int findMax(int* arr, int size)
{
int maxVal = arr[0];
for (int i = 1; i < size; i++)
if (arr[i] > maxVal)
maxVal = arr[i];
return maxVal;
}
// 修改数组内容(函数内修改会影响原数组)
void doubleArray(int arr[], int size)
{
for (int i = 0; i < size; i++)
arr[i] *= 2;
}
int main()
{
using namespace std;
int scores[] = {85, 92, 78, 96, 88, 73, 91};
int size = sizeof(scores) / sizeof(scores[0]); // 7
cout << "平均分:" << average(scores, size) << endl;
cout << "最高分:" << findMax(scores, size) << endl;
cout << "\n原数组:";
for (int i = 0; i < size; i++)
cout << scores[i] << " ";
cout << endl;
doubleArray(scores, size); // 修改原数组
cout << "翻倍后:";
for (int i = 0; i < size; i++)
cout << scores[i] << " ";
cout << endl;
return 0;
}
7.3.2 使用 const 保护数组
cpp
// const_array.cpp -- const保护数组参数
#include <iostream>
// const 防止函数意外修改数组
void printArray(const int arr[], int size)
{
for (int i = 0; i < size; i++)
std::cout << arr[i] << " ";
std::cout << std::endl;
// arr[0] = 999; // ❌ 编译错误!const保护
}
// 计算总和(只读,加const)
int sumArray(const int* arr, int size)
{
int sum = 0;
for (int i = 0; i < size; i++)
sum += arr[i];
return sum;
}
int main()
{
int data[] = {1, 2, 3, 4, 5};
printArray(data, 5);
std::cout << "总和:" << sumArray(data, 5) << std::endl;
return 0;
}
💡 最佳实践 :如果函数不需要修改数组,始终加
const,这样既保护数据,又明确了函数的意图。
7.3.3 使用指针范围传递数组
cpp
// pointer_range.cpp -- 用指针范围传递数组
#include <iostream>
// 传入首指针和尾后指针(类似STL风格)
double sumRange(const double* begin, const double* end)
{
double sum = 0;
for (const double* p = begin; p != end; p++)
sum += *p;
return sum;
}
int main()
{
using namespace std;
double prices[] = {9.9, 15.5, 23.0, 8.8, 12.3};
int size = 5;
// 传入首地址和尾后地址
double total = sumRange(prices, prices + size);
cout << "总价:" << total << endl;
// 只计算前3个
double partial = sumRange(prices, prices + 3);
cout << "前3个总价:" << partial << endl;
return 0;
}
7.4 函数与二维数组
cpp
// 2d_array_func.cpp -- 二维数组作为函数参数
#include <iostream>
const int COLS = 4; // 列数必须是常量
// 二维数组参数:必须指定列数
int sumMatrix(int matrix[][COLS], int rows)
{
int sum = 0;
for (int i = 0; i < rows; i++)
for (int j = 0; j < COLS; j++)
sum += matrix[i][j];
return sum;
}
void printMatrix(const int matrix[][COLS], int rows)
{
for (int i = 0; i < rows; i++)
{
for (int j = 0; j < COLS; j++)
{
std::cout.width(5);
std::cout << matrix[i][j];
}
std::cout << std::endl;
}
}
int main()
{
int mat[3][COLS] = {
{ 1, 2, 3, 4},
{ 5, 6, 7, 8},
{ 9, 10, 11, 12}
};
std::cout << "矩阵内容:" << std::endl;
printMatrix(mat, 3);
std::cout << "元素总和:" << sumMatrix(mat, 3) << std::endl;
return 0;
}
7.5 函数与字符串
cpp
// string_func.cpp -- 字符串作为函数参数
#include <iostream>
#include <cstring>
#include <cctype>
#include <string>
// C风格字符串:传入char指针
int countVowels(const char* str)
{
int count = 0;
while (*str)
{
char c = tolower(*str);
if (c=='a' || c=='e' || c=='i' || c=='o' || c=='u')
count++;
str++;
}
return count;
}
// string类:按值传递(会复制)
std::string toUpperStr(std::string s)
{
for (char& c : s)
c = toupper(c);
return s;
}
// string类:按引用传递(不复制,效率高)
void reverseStr(std::string& s)
{
int left = 0, right = s.size() - 1;
while (left < right)
{
std::swap(s[left], s[right]);
left++;
right--;
}
}
int main()
{
using namespace std;
const char* cstr = "Hello, World!";
cout << "元音字母数:" << countVowels(cstr) << endl; // 3
string str = "hello cpp";
cout << "转大写:" << toUpperStr(str) << endl;
cout << "原字符串:" << str << endl; // 未改变
reverseStr(str);
cout << "反转后:" << str << endl;
return 0;
}
7.6 函数与结构体
cpp
// struct_func.cpp -- 结构体作为函数参数
#include <iostream>
#include <string>
#include <cmath>
struct Point {
double x;
double y;
};
struct Rectangle {
double width;
double height;
};
// 按值传递结构体(会复制整个结构体)
double distanceBetween(Point p1, Point p2)
{
double dx = p2.x - p1.x;
double dy = p2.y - p1.y;
return sqrt(dx * dx + dy * dy);
}
// 按const引用传递(避免复制,推荐)
double area(const Rectangle& rect)
{
return rect.width * rect.height;
}
double perimeter(const Rectangle& rect)
{
return 2 * (rect.width + rect.height);
}
// 返回结构体
Point midpoint(Point p1, Point p2)
{
return {(p1.x + p2.x) / 2, (p1.y + p2.y) / 2};
}
int main()
{
using namespace std;
Point a = {0.0, 0.0};
Point b = {3.0, 4.0};
cout << "两点距离:" << distanceBetween(a, b) << endl; // 5
Point mid = midpoint(a, b);
cout << "中点:(" << mid.x << ", " << mid.y << ")" << endl;
Rectangle rect = {5.0, 3.0};
cout << "面积:" << area(rect) << endl; // 15
cout << "周长:" << perimeter(rect) << endl; // 16
return 0;
}
7.7 函数指针
7.7.1 什么是函数指针?
函数指针是指向函数的指针,可以将函数作为参数传递,实现回调机制。
函数指针声明格式:
返回类型 (*指针名)(参数类型列表);
例如:指向 double func(int) 的指针:
double (*pf)(int);
cpp
// func_pointer.cpp -- 函数指针基础
#include <iostream>
double square(double x) { return x * x; }
double cube(double x) { return x * x * x; }
double squareRoot(double x) { return sqrt(x); }
// 接受函数指针作为参数
void applyAndPrint(double x, double (*func)(double))
{
std::cout << "结果:" << func(x) << std::endl;
}
int main()
{
using namespace std;
// 声明函数指针
double (*pf)(double);
// 赋值:函数名就是函数地址
pf = square;
cout << "square(5) = " << pf(5) << endl; // 25
pf = cube;
cout << "cube(3) = " << pf(3) << endl; // 27
// 将函数指针作为参数传递
cout << "\n对 4.0 应用不同函数:" << endl;
applyAndPrint(4.0, square); // 16
applyAndPrint(4.0, cube); // 64
// 函数指针数组
double (*funcs[])(double) = {square, cube};
string names[] = {"square", "cube"};
cout << "\n函数指针数组:" << endl;
for (int i = 0; i < 2; i++)
cout << names[i] << "(3) = " << funcs[i](3) << endl;
return 0;
}
7.7.2 函数指针的实际应用:排序策略
cpp
// sort_strategy.cpp -- 函数指针实现排序策略
#include <iostream>
// 比较函数
bool ascending(int a, int b) { return a < b; } // 升序
bool descending(int a, int b) { return a > b; } // 降序
// 冒泡排序,接受比较函数指针
void bubbleSort(int arr[], int size, bool (*compare)(int, int))
{
for (int i = 0; i < size - 1; i++)
for (int j = 0; j < size - i - 1; j++)
if (!compare(arr[j], arr[j+1]))
std::swap(arr[j], arr[j+1]);
}
void printArray(const int arr[], int size)
{
for (int i = 0; i < size; i++)
std::cout << arr[i] << " ";
std::cout << std::endl;
}
int main()
{
using namespace std;
int data[] = {64, 34, 25, 12, 22, 11, 90};
int size = 7;
int asc_data[7], desc_data[7];
for (int i = 0; i < size; i++)
asc_data[i] = desc_data[i] = data[i];
bubbleSort(asc_data, size, ascending);
bubbleSort(desc_data, size, descending);
cout << "升序:"; printArray(asc_data, size);
cout << "降序:"; printArray(desc_data, size);
return 0;
}
7.8 递归函数
7.8.1 递归的基本概念
递归是函数调用自身的技术。每个递归函数必须有:
-
基准情形(Base Case):停止递归的条件
-
递归情形(Recursive Case):调用自身,向基准情形靠近
递归调用栈示意(factorial(4)):
factorial(4)
└─ 4 * factorial(3)
└─ 3 * factorial(2)
└─ 2 * factorial(1)
└─ 1(基准情形,返回1)
返回 21 = 2
返回 32 = 6
返回 4*6 = 24
cpp
// recursion_demo.cpp -- 递归函数示例
#include <iostream>
// 递归求阶乘
long long factorial(int n)
{
// 基准情形
if (n <= 1)
return 1;
// 递归情形
return n * factorial(n - 1);
}
// 递归求斐波那契数列
int fibonacci(int n)
{
if (n <= 0) return 0;
if (n == 1) return 1;
return fibonacci(n - 1) + fibonacci(n - 2);
}
// 递归求数组元素之和
int sumArray(const int arr[], int size)
{
if (size == 0) return 0; // 基准情形
return arr[0] + sumArray(arr + 1, size - 1); // 递归情形
}
int main()
{
using namespace std;
// 阶乘
for (int i = 0; i <= 10; i++)
cout << i << "! = " << factorial(i) << endl;
// 斐波那契
cout << "\n斐波那契数列前10项:";
for (int i = 1; i <= 10; i++)
cout << fibonacci(i) << " ";
cout << endl;
// 数组求和
int arr[] = {1, 2, 3, 4, 5};
cout << "\n数组求和:" << sumArray(arr, 5) << endl; // 15
return 0;
}
7.8.2 递归与迭代的对比
cpp
// recursion_vs_iteration.cpp
#include <iostream>
// 递归版本(简洁但有函数调用开销)
long long factRecursive(int n)
{
return (n <= 1) ? 1 : n * factRecursive(n - 1);
}
// 迭代版本(效率更高)
long long factIterative(int n)
{
long long result = 1;
for (int i = 2; i <= n; i++)
result *= i;
return result;
}
int main()
{
using namespace std;
for (int i = 1; i <= 12; i++)
{
cout << i << "! 递归=" << factRecursive(i)
<< " 迭代=" << factIterative(i) << endl;
}
return 0;
}
💡 递归 vs 迭代:
- 递归代码更简洁,适合树形结构、分治算法
- 迭代效率更高,无函数调用开销,无栈溢出风险
- 能用迭代解决的问题,优先考虑迭代
7.9 内联函数(inline)
内联函数是对编译器的建议 :将函数调用替换为函数体代码,避免函数调用开销,适合短小、频繁调用的函数。
cpp
// inline_demo.cpp -- 内联函数示例
#include <iostream>
// 普通函数:有函数调用开销
double square_normal(double x)
{
return x * x;
}
// 内联函数:编译器可能直接展开代码
inline double square_inline(double x)
{
return x * x;
}
// 内联函数适合短小的函数
inline int max2(int a, int b)
{
return (a > b) ? a : b;
}
inline bool isEven(int n)
{
return n % 2 == 0;
}
int main()
{
using namespace std;
// 调用方式与普通函数完全相同
cout << square_inline(5.0) << endl; // 25
cout << max2(10, 20) << endl; // 20
cout << boolalpha << isEven(7) << endl; // false
// 内联函数在循环中的优势
double sum = 0;
for (int i = 1; i <= 1000000; i++)
sum += square_inline(i); // 避免百万次函数调用开销
return 0;
}
💡 inline 注意事项:
inline只是对编译器的建议,编译器可以忽略- 函数体过长时,内联反而会增大代码体积
- 递归函数不能内联
- 通常定义在头文件中
7.10 引用变量与引用参数
7.10.1 引用的基本概念
引用是变量的别名,对引用的操作就是对原变量的操作。
cpp
// reference_basic.cpp -- 引用基础
#include <iostream>
int main()
{
using namespace std;
int a = 10;
int& ref = a; // ref 是 a 的引用(别名)
cout << "a = " << a << endl; // 10
cout << "ref = " << ref << endl; // 10
ref = 20; // 修改ref就是修改a
cout << "修改ref后,a = " << a << endl; // 20
// 引用和原变量共享同一地址
cout << "&a = " << &a << endl;
cout << "&ref = " << &ref << endl; // 地址相同!
// 引用必须在声明时初始化,且不能改变绑定
// int& r; // ❌ 错误:引用必须初始化
// ref = b; // 这是赋值,不是改变引用绑定
return 0;
}
7.10.2 引用参数(按引用传递)
cpp
// pass_by_reference.cpp -- 按引用传递
#include <iostream>
// 按引用传递:可以修改原变量
void swap(int& a, int& b)
{
int temp = a;
a = b;
b = temp;
}
// const引用:只读,不修改原变量(高效传递大对象)
double sumVector(const std::vector<double>& v);
// 对比三种传递方式
void byValue(int x) { x = 999; } // 修改副本,无效
void byPointer(int* x) { *x = 999; } // 修改原值
void byReference(int& x){ x = 999; } // 修改原值
int main()
{
using namespace std;
// 引用传递实现真正的交换
int x = 10, y = 20;
cout << "交换前:x=" << x << " y=" << y << endl;
swap(x, y);
cout << "交换后:x=" << x << " y=" << y << endl;
// 三种传递方式对比
int a = 0, b = 0, c = 0;
byValue(a);
byPointer(&b);
byReference(c);
cout << "\n按值传递后:a = " << a << endl; // 0(未改变)
cout << "按指针传递后:b = " << b << endl; // 999
cout << "按引用传递后:c = " << c << endl; // 999
return 0;
}
7.10.3 返回引用
cpp
// return_reference.cpp -- 返回引用
#include <iostream>
// 返回引用:可以作为左值
int& getElement(int arr[], int index)
{
return arr[index]; // 返回数组元素的引用
}
int main()
{
using namespace std;
int data[] = {10, 20, 30, 40, 50};
// 返回引用可以作为左值(赋值目标)
getElement(data, 2) = 999; // 修改data[2]
for (int i = 0; i < 5; i++)
cout << data[i] << " ";
cout << endl; // 10 20 999 40 50
// ⚠️ 不要返回局部变量的引用!
// int& badRef() {
// int local = 10;
// return local; // 危险!local在函数结束后销毁
// }
return 0;
}
7.11 默认参数
cpp
// default_params.cpp -- 默认参数示例
#include <iostream>
#include <string>
// 默认参数必须从右向左设置
void printInfo(std::string name,
int age = 18,
std::string city = "北京")
{
std::cout << "姓名:" << name
<< " 年龄:" << age
<< " 城市:" << city << std::endl;
}
// 计算幂次(默认平方)
double power(double base, int exp = 2)
{
double result = 1.0;
for (int i = 0; i < exp; i++)
result *= base;
return result;
}
int main()
{
using namespace std;
// 使用默认参数
printInfo("张三"); // age=18, city=北京
printInfo("李四", 25); // city=北京
printInfo("王五", 30, "上海"); // 全部指定
cout << "\npower(3) = " << power(3) << endl; // 9(默认平方)
cout << "power(3, 3) = " << power(3, 3) << endl; // 27
cout << "power(2, 10)= " << power(2, 10) << endl; // 1024
return 0;
}
💡 默认参数规则:
- 默认参数必须从右向左连续设置
- 默认参数通常在函数原型中指定,不在定义中重复
- 调用时,省略的参数使用默认值
7.12 函数重载
函数重载允许同名函数有不同的参数列表,编译器根据调用时的参数自动选择正确的版本。
cpp
// overload_demo.cpp -- 函数重载示例
#include <iostream>
#include <string>
// 同名函数,不同参数类型
void print(int x)
{
std::cout << "整数:" << x << std::endl;
}
void print(double x)
{
std::cout << "浮点数:" << x << std::endl;
}
void print(const std::string& s)
{
std::cout << "字符串:" << s << std::endl;
}
void print(int x, int y)
{
std::cout << "两个整数:" << x << ", " << y << std::endl;
}
// 重载的实际应用:求绝对值
int myAbs(int x) { return (x >= 0) ? x : -x; }
double myAbs(double x) { return (x >= 0) ? x : -x; }
int main()
{
using namespace std;
// 编译器根据参数类型自动选择版本
print(42); // 调用 print(int)
print(3.14); // 调用 print(double)
print(string("Hello")); // 调用 print(string)
print(10, 20); // 调用 print(int, int)
cout << "\nmyAbs(-5) = " << myAbs(-5) << endl; // 5
cout << "myAbs(-3.14)= " << myAbs(-3.14) << endl; // 3.14
return 0;
}
函数重载的匹配规则:
| 优先级 | 匹配类型 |
|---|---|
| 1(最高) | 完全匹配(类型完全一致) |
| 2 | 提升匹配(如 char→int,float→double) |
| 3 | 标准转换(如 int→double) |
| 4(最低) | 用户自定义转换 |
7.13 综合示例:学生成绩管理系统
cpp
// grade_system.cpp -- 综合示例
#include <iostream>
#include <string>
#include <fstream>
const int MAX_STUDENTS = 50;
struct Student {
std::string name;
int scores[3]; // 语文、数学、英语
double average;
char grade;
};
// 计算平均分
double calcAverage(const int scores[], int n)
{
int sum = 0;
for (int i = 0; i < n; i++)
sum += scores[i];
return (double)sum / n;
}
// 根据平均分确定等级
char getGrade(double avg)
{
if (avg >= 90) return 'A';
if (avg >= 80) return 'B';
if (avg >= 70) return 'C';
if (avg >= 60) return 'D';
return 'F';
}
// 打印单个学生信息
void printStudent(const Student& s)
{
std::cout << s.name << "\t"
<< s.scores[0] << "\t"
<< s.scores[1] << "\t"
<< s.scores[2] << "\t"
<< s.average << "\t"
<< s.grade << std::endl;
}
// 找最高平均分的学生
int findBest(const Student students[], int n)
{
int best = 0;
for (int i = 1; i < n; i++)
if (students[i].average > students[best].average)
best = i;
return best;
}
// 保存到文件
void saveToFile(const Student students[], int n,
const std::string& filename)
{
std::ofstream file(filename);
if (!file) { std::cout << "文件创建失败" << std::endl; return; }
file << "姓名\t语文\t数学\t英语\t平均\t等级" << std::endl;
for (int i = 0; i < n; i++)
file << students[i].name << "\t"
<< students[i].scores[0] << "\t"
<< students[i].scores[1] << "\t"
<< students[i].scores[2] << "\t"
<< students[i].average << "\t"
<< students[i].grade << std::endl;
std::cout << "数据已保存到 " << filename << std::endl;
}
int main()
{
using namespace std;
Student students[MAX_STUDENTS];
int n = 4;
// 初始化数据
students[0] = {"张三", {85, 92, 88}};
students[1] = {"李四", {90, 78, 95}};
students[2] = {"王五", {72, 85, 80}};
students[3] = {"赵六", {95, 98, 92}};
// 计算平均分和等级
for (int i = 0; i < n; i++)
{
students[i].average = calcAverage(students[i].scores, 3);
students[i].grade = getGrade(students[i].average);
}
// 打印成绩单
cout << "===== 学生成绩单 =====" << endl;
cout << "姓名\t语文\t数学\t英语\t平均\t等级" << endl;
cout << string(50, '-') << endl;
for (int i = 0; i < n; i++)
printStudent(students[i]);
// 找最优学生
int best = findBest(students, n);
cout << "\n最优学生:" << students[best].name
<< "(平均分:" << students[best].average << ")" << endl;
// 保存到文件
saveToFile(students, n, "grades.txt");
return 0;
}
输出:
===== 学生成绩单 =====
姓名 语文 数学 英语 平均 等级
--------------------------------------------------
张三 85 92 88 88.3333 B
李四 90 78 95 87.6667 B
王五 72 85 80 79 C
赵六 95 98 92 95 A
最优学生:赵六(平均分:95)
数据已保存到 grades.txt
📝 第7章知识点总结
| 知识点 | 核心要点 |
|---|---|
| 函数三要素 | 原型(声明)→ 定义(实现)→ 调用,原型让编译器做类型检查 |
| 按值传递 | 传递副本,函数内修改不影响原变量 |
| 数组参数 | 传递首元素地址,函数内可修改原数组,必须同时传入大小 |
| const 参数 | 只读参数加 const,保护数据并明确意图 |
| 结构体参数 | 小结构体按值传递,大结构体用 const& 引用传递 |
| 函数指针 | 返回类型 (*ptr)(参数类型),可将函数作为参数传递 |
| 递归 | 必须有基准情形,每次调用向基准靠近,注意栈溢出 |
| 内联函数 | inline 建议编译器展开,适合短小频繁调用的函数 |
| 引用参数 | 传递别名,函数内修改影响原变量,比指针更安全简洁 |
| 默认参数 | 从右向左设置,调用时可省略,通常在原型中声明 |
| 函数重载 | 同名不同参数,编译器根据参数类型自动选择版本 |