c++基础知识(5)

c++ primer plus 第七章,包括函数和数组、函数和二维数组、函数和字符串、函数和结构体、递归、函数指针。

复习函数的基本知识

定义函数

1
2
3
4
5
typeName functionName(parameterList)
{
statements
return value;
}

返回值不能是数组

函数原型:返回值类型+函数名+参数类型和个数

函数和数组

传递常规变量时,函数将使用该变量的拷贝;但传递数组时,函数将使用原来的数组(传递的是指向数组的指针)

1
2
3
4
void fillArray(int arr[], int size); //√
void fillArray(int *arr, int size); //√
void fillArray(int arr[size]); //×

使用原始数据增加了破坏数据的风险,通过c++中的const限定符提供了解决该问题的方法。

传递数组时:①传递数组的地址+数组大小;②传递数组的起始地址+数组的结尾地址

1
void fillArray(int *begin, int *end); //√

const

关于const的理解与用法:看const修饰的是*还是指针名

1
2
3
const int *pt; //
int *const pt;
const int *const pt;

const int *pt

1
2
int n = 10;
const int *pt = &n;

指针pt指向一个常量对象:pt指向一个const int,因此不能使用pt来修改这个值,换句话说*pt的值为const,不能被修改。然而,pt的声明并不意味着它指向的值实际上就是一个常量,而只是意味着对pt来说,这个值是常量。例如pt指向n,而n不是const,可以直接通过n变量来修改n的值,但是不能使用pt指针来修改它。

指向的内容可改,但不能通过这个指针修改

指针的指向可以修改

1
2
*pt = 20; //invalid
n = 20; //valid

int *const pt

1
2
int n = 10;
int const *pt = &n;

将指针本身声明为常量:可以通过指针pt修改其指向变量n的值,但不能修改pt本身的值,也就是不能改变pt的指向

const int *const pt;

不能通过pt指针修改其指向的值,且不能改变pt的指向。

函数和二维数组

如何将二维数组作为参数传递给函数?

假设有如下代码

1
2
3
4
5
6
int data[3][4] = {{1,2,3,4}, {9,7,5,3}, {2,3,4,5} };
int total = sum (data, 3); //data + count_row

//正确的函数原型:
int sum (int (*ar2)[4], int size);
//ar2是一个指针,该指针指向由4个int组成的数组

需要与之区分的是:

1
2
int *ar2[4]
// ar2是一个数组,该数组有4个元素,每一个元素是指向int的指针

函数与字符串

将字符串作为参数时,意味着传递的是地址。这意味着函数原型应将其表示字符串的形参声明为char *类型

1
2
3
4
5
6
7
char mmm[15] = "minium";
unsigned int ms = c_in_str(mmm, 'm');

unsigned int c_in_str(const char *str, char ch)
{
body
}

返回字符串的函数–>函数无法返回一个字符串,但可以字符串的地址。

函数和结构体

  1. 按值传递结构体,复制结构体增加内存要求,降低系统运行速度
  2. 传递结构体的地址,使用指针来访问结构体的内容

递归

递归:函数自己调用自己

1
2
3
4
5
6
7
void recurs(argumentlist)
{
statements1
if(test)
recurs(arguments)
statements2
}

递归调用将导致一系列有趣的事件。只要if语句为true,每个recurs()调用都将执行statements1,然后再调用recurs( ),而不会执行statements2。当if语句为false时,当前调用将执行statements2。当前调用结束后,程序控制权将返回给调用它的recurs(),而该recurs()将执行其stataments2部分,然后结束,并将控制权返回给前一个调用,依此类推。因此,如果recurs()进行了5次递归调用,则第一个statements1部分将按函数调用的顺序执行5次,然后statements2部分将以与函数调用相反的顺序执行5次。进入5层递归后,程序将沿进入的路径返回。

函数指针

将一个函数的地址作为另一个函数的参数

  1. 获取函数指针

    使用函数名(后面不跟参数)

    区分函数的地址和函数的返回值

  2. 声明一个函数指针

    1
    2
    3
    4
    5
    6
    7
    8
    // 函数原型
    double pam(int );
    // 正确的指针类型声明如下:pf是指向函数的指针
    double (*pf) (int);
    //错误的:pf是一个返回指针的函数
    double * pf(int);
    pf = pam;

  3. 使用函数指针来调用函数

    1
    2
    3
    4
    5
    6
    7
    double pam (int);
    double (*pf)(int);
    pf = pam;
    double x = pam(4);
    double y = (*pf)(5);
    // c++也允许像使用函数名一样使用pf
    double y = pf(5);

本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!