1 指针
1.1 *号的意义
*号:
- 在指针声明时,*号表示所声明的变量为指针。
- 在指针使用时,*号表示取指针所指向的内存空间中的值。

小贴士:

对于指针我们需要知道: - 指针是C语言中一种特别的变量。
- 指针所保存的值是内存的地址。
- 可以通过修改指针修改内存中的任意地址内容。

1.2 传值调用与传址调用
传值调用与传址调用:
- 指针是变量,因此可以声明指针参数。
- 当一个函数体内部需要改变实参的值,则需要使用指针参数。
- 函数调用时实参值将复制到形参。
- 指针适用于复杂数据类型作为参数的函数中。
#include <stdio.h>
int swap(int* a, int* b)
{
int c = *a;
*a = *b;
*b = c;
}
int main()
{
int aa = 1;
int bb = 2;
printf("aa = %d, bb = %d\n", aa, bb);
swap(&aa, &bb);
printf("aa = %d, bb = %d\n", aa, bb);
return 0;
}
2 指针的运算与比较
2.1 指针与整数的运算
指针是一种特殊的变量,与整数的运算规则如下:

结论: 当指针p指向一个同类型的数组的元素时,p+1将指向当前元素的下一个元素;p-1将指向当前元素的上一个元素。
2.2 指针之间的运算
指针之间只支持减法运算,参与减法运算的指针类型必须相同。

注意:
- 只有当两个指针指向同一个数组中的元素时,指针相减才有意义,其意义为指针所指元素的下标差。
- 当两个指针指向的元素不在同一个数组中时,结果未定义。
2.3 指针的比较
指针的比较:
- 指针可以进行关系运算(<,<=,>,>=)。
- 指针关系运算的前提是同时指向同一个数组中的元素。
- 任意两个指针之间的比较运算(==、!=)无限制。
- 参与比较运算的指针类型必须相同。
指针运算示例:
#include <stdio.h>
int main()
{
char s1[] = {'H', 'e', 'l', 'l', 'o'};
int i = 0;
char s2[] = {'W', 'o', 'r', 'l', 'd'};
char* p0 = s1;
char* p1 = &s1[3];
char* p2 = s2;
int* p = &i;
printf("%d\n", p0 - p1);
printf("%d\n", p0 + p2); // error
printf("%d\n", p0 - p2); // 结果未定义
printf("%d\n", p0 - p); // error
printf("%d\n", p0 * p2); // error
printf("%d\n", p0 / p2); // error
return 0;
}
指针运算的应用:
#include <stdio.h>
#define DIM(a) (sizeof(a) / sizeof(*a))
int main()
{
char s[] = {'H', 'e', 'l', 'l', 'o'};
char* pBegin = s;
char* pEnd = s + DIM(s); // Key point
char* p = NULL;
printf("pBegin = %p\n", pBegin);
printf("pEnd = %p\n", pEnd);
printf("Size: %d\n", pEnd - pBegin);
for(p=pBegin; p<pEnd; p++)
{
printf("%c", *p);
}
printf("\n");
return 0;
}
3 二级指针
3.1 指向指针的指针
基本概念:
- 指针的本质是变量。
- 指针会占用一定的内存空间。
- 可以定义指针的指针来保存指针变量的地址值。

为什么需要指向指针的指针?
- 指针在本质上也是变量。
- 对于指针也同样存在传值调用与传址调用。
二级指针的应用:重置动态空间大小
#include <stdio.h>
#include <malloc.h>
int reset(char**p, int size, int new_size)
{
int ret = 1;
int i = 0;
int len = 0;
char* pt = NULL;
char* tmp = NULL;
char* pp = *p;
if( (p != NULL) && (new_size > 0) )
{
pt = (char*)malloc(new_size);
tmp = pt;
len = (size < new_size) ? size : new_size;
for(i=0; i<len; i++)
{
*tmp++ = *pp++;
}
free(*p);
*p = pt;
}
else
{
ret = 0;
}
return ret;
}
int main()
{
char* p = (char*)malloc(5);
printf("%p\n", p);
if( reset(&p, 5, 3) )
{
printf("%p\n", p);
}
free(p);
return 0;
}
参考资料:
1178

被折叠的 条评论
为什么被折叠?



