指针

1、什么是指针?

通俗来讲——指针就是变量,用来储存地址的变量。

2、指针数组 & 数组指针

指针数组:它是一个数组,数组里面每个元素都是指针,数组的大小由它元素的个数决定。 

数组指针:它是一个指针,它指向一个数组,指针的大小永远都是4字节 。

(1)int *p1[10] 

p1是指针数组,里面有10个元素,每个元素都是地址;

(2)int (*p2)[10] 

p2是数组指针,这个指针指向一个有10个整型元素的数组。

两者区分:

①我们要知道“[ ]”的优先级比“ * ”的优先级高,p1先与“[ ]”先集合,这就构成了数组的结构,数组名是p1,里面存的元素的类型是 int *

②p2先和“ * ”结合,构成指针结构,指针名为p2,int和[10]共同表示指针的类型,p2指向的是具有10个整型元素的数组。

3、a和&a的区别

int main()

{

    char a[5] = { 'a', 'b', 'c', 'd', 'e' };

    char(*p1)[5] = &a;

    char(*p2)[5] = a;

    return 0;

}

p1和p2哪个是数组指针?

此处p1和p2都是数组指针,但最好采用p1这种写法。 因为a是代表数组首元素的地址,而&a才是代表整个数组的地址,两者的值是一样的,但所代表的意义是完全不同的。

4、地址强转

下面代码输出结果是多少?

int main()

{

    int a[4] = { 1, 2, 3, 4 };

    int *p1 = (int *)(&a + 1);

    int *p2 = (int *)((int)a + 1);

    printf("%x, %x", p1[-1], *p2);

    return 0;

}

p1:把 &a+1的值强制转换成 int * 再赋值给p1,此时p1指向数组a尾元素的下一个int型元素。p1[-1]可以理解成 *(p1 - 1)。表示p1往前移动sizeof(int)个字节,所以输出0x4。

p2:(int)a + 1表示把a强转成整型数据,再加1则(int)a + 1就是元素a[0]的第二个字节的地址,然后再把这个地址强转为int * 类型赋值给p2,那*p2的值就是从元素a[0]的第二个字节开始的连续4字节的内容。

那么这连续4个字节内容是什么呢?这里就要区分大小端了,小端模式返回0x2000000;大端模式返回0x100。

注:

所谓的大端模式,就是高位字节排放在内存的低地址端,低位字节排放在内存的高地址端。

所谓的小端模式,就是低位字节排放在内存的低地址端,高位字节排放在内存的高地址端。

5、函数指针

函数指针还是一个指针,它指向的是一个函数,这个指针变量里存的是一个函数的地址。

char * ( *fun)(char *p1, char *p2);

这里定义了一个函数指针,指针名为fun,指向函数fun,这个函数的返回值类型是 char *,参数是char *p1, char *p2。

函数指针数组:

char * ( *pf)(char *p)这里定义了一个函数指针 pf,既然如此那把这个指针放到数组里,这就形成了一个函数指针数组:

char * ( * pf[10])(char *p)

①数组名:pf

②数组元素:10个指向函数的指针。

③每个指针指向一个函数

④函数的返回类型为指向字符的指针,参数为一个指向字符的指针。

函数指针数组的用途:转移表

函数指针数组指针:

函数指针数组指针就是一个指针, 这个指针指向一个数组,这个数组里存的是指向函数的指针。

char * ( * (*pf)[10]) (char * p)

①这里定义了一个函数指针数组指针,指针变量名是pf。

②指针指向一个有10个元素的数组。

③数组里存的都是指向函数的指针。

④ 这些指针每个都指向一些函数。

⑤指向的函数的返回值类型为指向字符的指针,参数为一个指向字符的指针。

记忆方法:

函数指针数组指针数组指针。

我们从右往左分析:

①指针:*pf

②数组指针:(* pf)[5]

③指针数组指针:(* (* pf) )[5]

④数组指针数组指针:( (* (* pf) )[5])[3]

⑤指针数组指针数组指针:( * ( (* (* pf) )[5]) )[3]

⑥函数指针数组指针数组指针:void * ( ( * ( (* (* pf) )[5]) )[3] ) ( )

分析(*(void(*)())0)()

①void(*)() 是一个函数指针类型,这个函数无参数,无返回值。

②(void(*)())0 把0强转成函数指针类型,0是一个函数的首地址。

③(*(void(*)())0) 把地址为0的函数取出来。

④(*(void(*)())0)(),函数调用。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 指针是C语言中广泛使用的一种数据类型。 运用指针编程是C语言最主要的风格之一。利用指针变量可以表示各种数据结构; ...
    朱森阅读 3,514评论 3 44
  • 第十章 指针 1. 地址指针的基本概念: 在计算机中,所有的数据都是存放在存储器中的。一般把存储器中的一个字节称为...
    坚持到底v2阅读 1,105评论 2 3
  • 前言:指针是 C语言一个重要概念,也是C 语言的一个重要特色。使程序简洁、紧凑、高效。指针乃是C之精华。 数据在内...
    潇湘候晨雪阅读 790评论 0 0
  • 1. 变量 不同类型的变量在内存中占据不同的字节空间。 内存中存储数据的最小基本单位是字节,每一个字节都有一个内存...
    C语言学习阅读 1,329评论 0 4
  • !!!注意:因为简书的显示格式缘故,所以“ * ”显示会出现问题,可能有些星号由于疏忽未改动格式,造成没有显示,请...
    Eric_Hunter阅读 734评论 0 0