目录
1.指针基础知识
2.字符指针
3.指针数组
1.指针基础知识
1.指针就是一个变量,用来存放地址,地址唯一标识一块内存空间。
(不同的指针可以指向同一块的空间,但是指针只可以指向一块空间)
2.指针的大小是固定的4/8个字节(32位平台/64位平台)。
3.指针是有类型的,指针的类型决定了指针的+整数的步长,指针解引用操作的时候的权限。
(我对于指针的解引用的理解是,就是该地址对应的东西解开,就像送的快递包裹一样,先找寻到相应的地址,然后把包裹解开才能拿到里面的东西,而不同的类型,包裹的大小是不同,根据的类型的不同,可以得到你需要引用多长的字节内容)
4.指针的运算。
(我们重点研究了解指针有关内存管理的内容)
2.字符指针
在指针的类型中我们要知道有一种指针类型为字符指针char*;
我们先看单字符指针:
简单来说就是,先字符变量pr中放入字符W,然后字符指针存放。pr地址,最后再解引用字符指针cp。下面我们视频形象的理解。
博客草稿本
还有一种使用方式如下:
int main()
{
const char* post = "hello,world";//这里是把整个字符串放进post指针变量里面吗?
printf("%s", post);
return 0;
}
这里特别容易让大家以为是将字符串”hello world“放到字符指针post里面,其实本质上是将字符串hello,world 的首字符的地址放到了post里面。
有这样一个面试题:
#includeint main() { char str1[] = "hello world."; char str2[] = "hello world."; const char *str3 = "hello world."; const char *str4 = "hello world."; if(str1 ==str2) printf("str1 and str2 are samen"); else printf("str1 and str2 are not samen"); if(str3 ==str4) printf("str3 and str4 are samen"); else printf("str3 and str4 are not samen"); return 0; }
最后输出这样一个结果:(str1 != str2) (str3 == str4)
下面我们来分析一下其中的原理:str1 与str2 都是数组的形式,数组名存储字符串的首字符地址。但是数组的存储原理是开辟一块空间。这与指针指向性的特性是最本质的区别,也是问题的所在。
下面我们用图片来形象的理解。
3.指针数组
指针数组是指一个数组里面的元素都是指针。注意这个点,这是与其他形式的数组本质上的区别。
指针数组的定义形式一般为:
dataType *arrayName[length];
其他[ ] 的优先级比 * 的高所以也可以这样理解
dataType *(arrayName[length]);
其实在我们所看见的数组比如 arr[3] 这样的类型也可以表示为*(arr + 3)。
看上面这一张图片,我们初始化arr数组,当我们需要数组中下标为1的数值时,我们也可以用这样的形式,这里我们可以把数组名当作是一个指针(但是他本质上并不是指针,可以理解为在这种形式下他被转化为了指针,但是并不是指针)arr数组名代表数组中第一个元素也就是下标为0的元素,(arr+1)数组名就指向了下标为1的元素,再进行解引用操作得到下标为1的数值。
我们再回到上面的指针数组的形式:
dataType *arrayName[length];
这里是不是对 *arrName[length] 这样的形式更好的理解;这里dataType代表的是数据类型,arrName代表的数组名,length代表的是长度。
其实除了数组中数据类型的不同,其他都是一样的,下面我们举一个例子来理解:
#includeint main() { int a = 12, b = 13, c = 14; int* arr[3] = { &a, &b, &c };//每个元素存放相应的地址 printf("%d, %d, %dn", *arr[0], *arr[1], *arr[2]); printf("%d, %d, %dn", **(arr), **(arr + 1), **(arr + 2)); return 0; }
输出的结果都是一样的,都是12,13,14。
下面我们需要讨论的是为什么这二个形式会输出一样的结果。我们先看第一个:
我们由图片可以知道,arr[lengrh]就是数组中的元素,但是指针数组中数组里面的元素都是指针,这时我们需要进行解引用操作,*arr[length]得到相应的值。我们再看第二个:
由图片我们可以看出,我们可以把数组名看成是一个指针比如arr指向的是arr[0]的地址,我们进行解引用得到了arr[0]这个值,arr[0]就是&a,然后我们得到了变量a的地址,再进行解引用得到了12这个数值。
指针数组还可以和字符串数组结合使用,比如:
#includeint main() { char* str[3] = { "hello,world", "hello,CSDN", "hello,bit" }; printf("%sn,%sn,%sn", str[0], str[1], str[2]); return 0; }
需要注意的是,字符数组 str 中存放的是字符串的首地址,不是字符串本身,字符串本身位于其他的内存区域,和字符数组是分开的。
也只有当指针数组中每个元素的类型都是char *时,才能像上面那样给指针数组赋值,其他类型不行。
在下一期中,会对数组指针进行深度解剖。



