c基础-指针

1概念

(1).32位,有2的32次方个内存单元。64位有2的64次方个内存单元。

(2).一个内存单元存放大小为1个字节(byte)

(3).指针就是地址,内存空间由多个内存单元组成,每个内 存单元由一个或多个字节组成,每个字节都有一个唯一 的编号,这个编号地址 在不影响理解的情况中,有时对地址、指针和指针变量 不区分,通称指针。

(4)指针大小(sizeof(char*)/sizeof(int*))是相同的:因为指针需要多大空间,取决于地址的存储需要多大空间。

32位-32bit-4byte

64位-64bit-8byte

1.1取地址与解引用

1.打印地址:

int a = 10;//内存分配4个字节地址
printf("%p\n",&a);//用%p打印a的首地址
int* pa = &a;
//pa用来存放a的地址,在c语言中pa叫指针变量
//*说明 pa是指针变量
//int说明pa执行的对象是int类型
return 0;

此时pa = &a

2.解引用:

int a = 10;
int* pa = &a;
*pa = 20;//解引用操作,*pa通过pa里面的地址找到a

此时*pa = a

1.2指针类型的意义 

1.指针类型决定了:指针解引用的权限有多大

char*:访问1个字节。

int*:访问4个字节。

eg:

int a = 0x11223344;
分别用4个字节表示为: 44 33 22 11

char* pc = &a;

*pc = 0;
//此时char类型的*pc只能访问int类型a的一个字节(44)
所以只改变个字节 : 00 33 22 11

       

         注意:一个十六进制位要4个二进制位(4位)表示,所以两个十六进制占8位(8个二进制),而8位表示一个字节。   

        所以在0x11223344中:11表一个字节,22表一个字节,33表一个字节,44表一个字节)

2.指针类型决定了,指针走一步,能走多远(步长)

 eg:

注:p是从当前位置开始加减的,可以理解为下标为1.而arr是从0开始加减的。

  9 int main(int argc, char *argv[])
 10 {
 11     int arr[5] = {1,2,3,4,5};
 12     int* p = arr;
 13     printf("%d\n",arr[2]);
 14     printf("%d",*(p+2));
 15 
 16     return 0;
 17 }

3
3

 但是,从数组角度来看,p+n,数据就从0开始移动n位。

1.3野指针 

野指针是指指针指向的位置不可知。

1.

int* p;//p是一个局部的指针变量,局部变量不初始化的话,默认是随机值。

*p = 20;//非法访问


2.越界

int arr[10] = {0};
int* p =arr;
int i = 0;
for(i = 0;i<=10;i++)
{
    *p = i;
     p++;
}

二.各种指针介绍

2.1字符指针

//1.
char ch = 'q';
char* pc = &ch;

//2:
char* ps = "hello word";
printf("%c",*ps);
--->h
//也可以打印字符串
printf("%s",ps);
printf("%s",arr);
因为(%s)打印字符数组时,给了起始地址,会把剩下的都打印下来。

对于(2:)ps存放的是字符串的第一个地址。

例题:

  7 #include <stdio.h>
  8 
  9 int main(int argc, char *argv[])
 10 {
 11     int a[5] = {1,2,3,4,5};
 12     int b[5] = {1,1,1,1,1};
 13     int c[5] = {2,2,2,2,2};
 14     int* arr[3] = {a,b,c};
 15 
 16     for(int i = 0;i<3;i++){
 17         for(int j = 0;j<5;j++){
 18             printf("%d",*(arr[i]+j));//arr[i][j];因为[j] = *( +j);
 19         }
 20         puts("");
 21     }
 22 
 23 
 24 
 25     return 0;
 26 }


hqyj@ubuntu:~/c/day11$ ./a.out
12345
11111
22222

2.2指针数组

int*  arr[3];存放整型数组

2.3数组指针

arr与&arr区别

1.表示的结果都是表示数组的首地址

2.但存入内存的表达方式不一样

int arr[10]={0};

int* p1 = arr;
存入的是一个指针,用int类型指针p1指向arr首地址。p1是一个整型指针。

int (*p2)[10]= &arr
p2是一个数组指针。
&arr表示一整行数组,此p2就是相当于指向了arr一整行数组。上升到到二维数组,arr[10][5](相当于10个一维数组,每一行5个数据),p2相当于指向了arr这个二维数组的第一行。


??为什么p2要的是一个数组指针?
??p2是指向arr的每一个地址吗?

2种arr不表示首地址的情况

1.sizeof(arr),表示整个数组,计算整个数组的大小。

2.&arr。数组名表示整个数组,是取整个数组的地址。

2.3.1一维数组指针 

arr[ ]  int* p

1.arr是常量指针,所以不可以arr++,可以arr+n;

2.p是变量指针,所以可以p++实现移位

eg:

arr[2]在编译器编译的时候,会把arr[2]变成解引用---->*(arr + 2)

p[2] ----> *(p+2)

2.3.2二维数组指针

二维数组的首地址是第一行

二维数组名是行指针 

229行:传入的是arr,表示数组首元素地址,而首元素是第一行,所以传入的是一个一维数组地址。

209行:用一个指向一维数组的指针p来接受该地址。

217行:用p+i找到第i行地址;*()称为解引用,表示找到i行的数组地址,等于找到了第i行首元素地址;首元素地址+j,表示该行j元素的地址;最后再*(),表示解引用(i行j列)地址,获得该地址的数据。

*(p+i)中,*表示解第i行引用,获得的是数组名。

q+1:是行加1,及q+1 == q+4*7(int 占4个字节) 

  • 16
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值