数组与指针SOFT


数组


(1)数组:聚合类型,是一组有序数据的集合。
(2)用一个数组名和下标,来唯一确定数组中的元素。
(3)数组中的每一个元素都属于同一种类型。

(4)定义一位数组的一般形式:

类型符 数组名[常量表达式]

  • C语言中不允许对数组的大小做动态定义,如int a[n]

(5)引用数组元素的一般形式:

数组名[下标]

(6)一维数组的初始化:

  • 未初始化时其值为随机值,初始化后无值的为0;
  • 初始化只有一次,赋值时不可以用数组名赋值给数组名,如:arr = brr;

(7)由于局部变量存放在栈中,栈是由高地址向低地址存放,数组存放时先在栈中开辟连续内存,因此,arr[0]在低位,arr[1]在高位;

(8)数组名代表数组首元素的首地址;

  • 数组名不能做为左值,我们只能访问数组的某个元素而无法把数组当一个总体进行访问,所以我们可以把a[i]当左值,而无法把a当左值;
  • 数组名作为右值代表数组首元素的首地址,意义与&a[0]一样,同样不代表数组的首地址。
  • 数组名的含义:
    • &arr + 1 -> 数组的长度
    • sizeof(arr) -> 数组的长度
    • sizeof(arr[0]) -> 数组类型的长度
    • sizeof(&arr) -> 数组类型的长度
    • sizeof(&arr[0]) -> 数组类型的长度

注:数组中arr –&arr–&arr[0]表示的值是一样的。

(9)在数组中,表示数组长度的方式有:&arr+1;sizeof(arr)/sizeof(arr[0]);

  • 仅在数组定义后求长才可以求得长度;
  • 在功能函数里不能求长度,arr仅是指针;

补:哨兵位:禁止数组越界,arr与int,int与int相差两个四字节;(VC没有哨兵位,VC中栈是连续的,没有栈保护)

(10)字符数组:

  • 字符数组初始化后无值的为’\0’;
  • 以字符串形式%s输出时,遇’\0’终止;
    例:
char arr[5] = {'d','u','a','n','g'};//输出不停止
char brr[] = {'d','u','a','n','g','\0'};
char crr[5] = {'d','u'};
char drr[6] = "duang";
char err[] = "duang";
printf("%s,%s,%s,%s,%s\n",arr,brr,crr,drr,err);

char arr


指针


(1)指针变量里存放的是指向变量的地址。
* 解引用,间接访问符;可以访问指向变量的值。
例:

int a = 10;
int *p = &a;
int **pp = *p;
printf("%d,%d,%d,%d,%d\n",a,p,pp,*p,**p);
*p = 20;
printf("%d\n",a);
**pp = 30;
printf("%d\n",a);

***

(2)交换函数问题

void Swap1(int a,int b)
{
    int tmp = a;
    a = b;
    b = tmp;
}
void Swap2(int *p,int *q)
{
    int *tmp = NULL;//野指针
    *tmp = *p;
    *p = *q;
    *q = *tmp;
}
void Swap3(int *p,int *q)//正确版本
{
    int tmp = *p;
    *p = *q;
    *q = tmp;
}
void Swap4(int *p,int *q)
{
    int *tmp = p;
    p = q;
    q = tmp;
}

void main()
{
    int a = 1,b = 2;
    Swap1(a,b);
    printf("%d,%d\n",a,b);//1,2
    Swap2(&a,&b);
    printf("%d,%d\n",a,b);//崩溃
    Swap3(&a,&b);
    printf("%d,%d\n",a,b);//2,1
    Swap4(&a,&b);
    printf("%d,%d\n",a,b);//1,2
}

分析:

  • Swap1函数—>参数传递过程中,只对参数的值进行了传递,所以功能函数内部进行交换操作时,并没有改变主函数参数的值。
  • Swap2函数—>功能函数内部产生野指针,野指针没有指向值,tmp解引用时因无值而崩溃;所以*tmp= *p;语句不能够执行。
  • Swap3函数—>完美执行。
  • Swap4函数—>功能函数里的交换操作是对参数的指针来进行操作的,并没有改变参数本身的值。

注:野指针—int *tmp;/ = NULL;

  • 指针变量未初始化
    任何指针变量刚被创建时不会自动成为NULL指针,它的缺省值是随机的,会乱指一气。
    所以指针在创建的同时应当被初始化,要么赋值为NULL,要么让它指向合法内存。
  • 指针释放后未置空
    指针在free或者delete后未赋值为NULL,free和delete只是把指针所指向的内存释放掉,并没有把指针清除,此时指针指向的为垃圾内存。
    为防止野指针,内存释放后,指针应立即指向NULL。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值