主要介绍以下内容
- 1. 字符指针
- 2. 数组指针
- 3. 指针数组
- 4. 数组传参和指针传参
- 5. 函数指针
- 6. 函数指针数组
- 7. 指向函数指针数组的指针
- 8. 回调函数
一、字符指针
int main()
{
char ch = 'w';
char* pc = &ch;
const char* p = "abcdef";//常量字符串(不能修改)
//实际把首字符a的地址放到p里
printf("%s\n", p);//abcdef(%s打印字符串:起始位置到\0结束)
return 0;
}
在指针的类型中我们知道有一种指针类型为字符指针
char*
二、指针数组(是数组,存放的指针)
int main()
{
//存放字符指针的数组
const char* arr[4]={"abcdef","qwer","hello","hehe"};//const更加严谨
int i = 0;
for (i = 0; i < 4; i++)
{
printf("%s\n", arr[i]); //打印指针数组中的所有内容
}
return 0;
}
三、数组指针
int main()
{
char ch = 'w';
char* pc = &ch;
int num = 10;
int* pi = #
int arr[10];
//pa就是数组指针
int(*pa)[10] = &arr;
return 0;
}
- 数组指针的本质是指针,指的是能够指向数组的指针。
(一)&数组名VS数组名
int main()
{
int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };
printf("%p\n", arr);
printf("%p\n", arr + 1);
printf("%p\n", arr[0]);
printf("%p\n", arr[0] + 1);
printf("%p\n", &arr);
printf("%p\n", &arr + 1);
return 0;
}
- &arr 表示的是数组的地址,而不是数组首元素的地址
- 数组的地址+1,跳过整个数组的大小,所以 &arr+1 相对于 &arr 的差值是40.
(二)数组指针的使用
void print1(int arr[3][4], int r, int c)
{
int i = 0;
for (i = 0; i < r; i++)
{
int j = 0;
for (j = 0; j < c; j++)
{
printf("%d ", arr[i][j]);
}
printf("\n");
}
}
void print2(int(*p)[4], int r, int c)//数组指针
{
int i = 0;
for (i = 0; i < r; i++)
{
int j = 0;
for (j = 0; j < c; j++)
{
//printf("%d ", (*(p + i))[j]);
printf("%d ", p[i][j]);
}
printf("\n");
}
}
int main()
{
int arr[3][4] = { {1,2,3,4}, {2,3,4,5} , {3,4,5,6} };
print1(arr, 3, 4);
print2(arr, 3, 4);//数组名代表首元素地址(对于二维数组来说就是第一行)
return 0;
}
注:一维数组当作一个元素
四、数组参数、指针参数
(一)一维数组传参
(二)二维数组传参
(三)一级指针传参
void print(int* p, int sz)
{
int i = 0;
for (i = 0; i < sz; i++)
{
printf("%d\n", *(p + i));
}
}
int main()
{
int arr[10] = { 1,2,3,4,5,6,7,8,9 };
int* p = arr;
int sz = sizeof(arr) / sizeof(arr[0]);
//一级指针p,传给函数
print(p, sz);
return 0;
}
(四)二级指针传参
void test(int** ptr) //二级指针接收
{
printf("num = %d\n", **ptr);
}
int main()
{
int n = 10;
int* p = &n;
int** pp = &p;
test(pp);//二级指针传参
test(&p);
return 0;
}
五、函数指针
int Add(int x, int y)
{
return x + y;
}
int main()
{
//int (*pf)(int, int) = &Add;//函数名和&函数名都是表示函数的地址
int (* pf)(int, int) = Add;//pf 是一个存放函数地址的指针变量 - 函数指针
//int ret = Add(2, 3);
int ret = pf(2, 3);
printf("%d\n", ret);
return 0;
}
六、函数指针数组
列举:指针数组;数组指针;函数指针;函数指针数组
int my_strlen(const char* str)
{
return 0;
}
int main()
{
//指针数组
char* ch[5];
int arr[10] = {0};
//pa是数组指针
int (*pa)[10] = &arr;
//pf是函数指针
int (*pf)(const char*) = &my_strlen;
//函数指针数组
int (*pfA[5])(const char*) = { &my_strlen};
return 0;
}
函数指针数组的用途——转移表(计算器)
七、指向函数指针数组的指针
指向函数指针数组的指针是一个 指针
指针指向一个 数组 ,数组的元素都是函数指针
int main()
{
int arr[10];
int (*pA)[10] = &arr;
//函数指针数组
int (* pf[5])(int, int);
//ppf是指向函数指针数组的指针
int (*(* ppf)[5])(int, int) = &pf;
return 0;
}
八、回调函数
回调函数就是一个通过函数指针调用的函数。如果你把函数的指针(地址)作为参数传递给另一个
函数,当这个指针被用来调用其所指向的函数时,我们就说这是回调函数。回调函数不是由该函数
的实现方直接调用,而是在特定的事件或条件发生时由另外的一方调用的,用于对该事件或条件进
行响应。
应用:计算器(转移表)
qsort函数