zoukankan      html  css  js  c++  java
  • C语言基础学习4:数组与指针

    数组元素的指针就是数组元素的地址。

    1、指向数组元素的指针

    C语言规定数组名(不包括形参数组名,形参数组并不占据实际的内存单元)代表数组中的首元素(即序列为0的元素)的地址。

    int a[10];
    int *p1,*p2;
    p1 = &a[0];
    p2 = a;

    p1和p2指向同一个数组a[10]。

    2、通过指针引用数组元素

    按C语言的规定,如果指针变量p已指向数组中的一个元素,则p+1指向同一个数组中的下一个元素,而不是将p的值(地址)简单的加1。

    如果p的初值为&a[0],则

    (1) p+i 和 a+i就是a[i]的地址。

    (2) *(p+i) 或 *(a+i)是p+i 和 a+i 所指向的数组元素,即a[i]。

    (3)指向数组的指针变量也可以带下标,如p[i]与*(p+i)等价。

    for(p=a;p<a+10;p++)
       printf("%d",*p);

    (4)可以通过改变指针变量指向不同的元素。注意上面的p++不能改为a++,原因是数组a虽然也代表数组首元素的地址,但它是一个指针常量,它的值在程序运行期间是固定不变的。

    (5)注意指针的指向。

    #include <stdio.h>
    void main()
    {
        int *p,i,a[10];
        p = a;
        for(i=0;i<10;i++)
            scanf("%d",p++);
        printf("
    ");
        p = a; //作用是将指针的位置重新定位到数组首地址处
        for(i=0;i<10;i++,p++)
        {
            printf("%d",*p);
            printf("
    ");
        }
        return;
    }

    (6)注意指针变量的运算

    i.p++或(p+=1).使p指向下一元素,即a[1]。若再执行*p,则得到下一个元素a[1]的值。

    ii.*p++。由于++和*同优先级,结合方向为自右向左,因此它等价于*(p++)。作用是先得到p指向的变量即(*p),然后再使p+1.

    for(i=0;i<10;i++)
        printf("%d",*p++);

    与(3)等价。

    iii.*(p++)与*(++p)作用不同。前者是先取*p值,然后使p加1.后者是先使p+1,然后再取*p。若p初值为a(即&a[0]),则*(p++)为a[0],*(++p)为a[1]。

    iv.++(*p)表示p所指向的元素值加1,如果p=a,则++(*p)相当于++(a[0]),注意是元素a[0]加1,不是指针p加1。

    v.如果p当前指向a数组中第i个元素,则

    *(p--)相当于a[i--],先对p进行*运算,再使p自减。

    *(++p)相当于a[++i],先使p自加,再作*运算。

    *(--p)相当于a[--i],先使p自减,再作*运算。

    3、用数组名作为函数参数

    实参数组名代表一个固定的地址,或者是指针常量,但形参数组并不是一个固定的地址值,而是作为指针变量,并不是真正地开辟一个数组空间,在函数调用开始时,它的值等于实参数组首元素的地址,在函数执行期间,它可以再被赋值。实参和形参都可以使用数组名或指针变量。

    4、多维数组与指针

    4.1多维数组元素的地址

    int a[3][4] = {{1,3,5,7},{9,11,13,15},{17,19,21,23}};

    a 是数组名,从二位数组的角度来看,a代表二位数组首元素的地址,现在的首元素不是一个简单的整型元素,而是由4个整型元素所组成的一维数组,因此a代表的是首行(即第0行)的首地址。a+1表示第一行的首地址,a+2表示第二行的首地址。

    a[0],a[1],a[2]既然是一维数组名,而C语言又规定了数组名代表数组首元素地址,因此a[0]代表一维数组a[0]中第0列元素的地址,即&a[0][0],a[1]的值是&a[1][0],a[2]的值是&a[2][0]。a[0]是一维数组名,该一维数组中序号为1的元素的地址是a[0]+1,a[0]和a[0]+1实际上是a[0][0]和a[0][1]的地址。

    a[0]与*(a+0)等价,a[1]和*(a+1)等价,a[i]和*(a+i)等价。因此a[0]+1和*(a+0)+1都是&a[0][1]。

    进一步,*(a[0]+1)和*(*(a+0)+1)就是a[0][1]的值。

    *(a[i]+j)或*(*(a+i)+j)是a[i][j]的值。

    表示形式 含义 地址
    a 二维数组名,指向一维数组a[0],即0行首地址 2000
    a[0],*(a+0),*a 0行0列元素地址 2000
    a+1,&a[1] 1行首地址 2008
    a[1],*(a+1) 1行0列元素a[1][0]的地址 2008
    a[1]+2,*(a+1)+2,&a[1][2] 1行2列元素a[1][2]的地址 2012

    *(a[1]+2),*(*(a+1)+2),a[1][2]

    1行2列元素a[1][2]的值 元素值为13

     

     

     

     

     

     

     

     

    4.2 指向多维数组元素的指针变量

    (1)指向数组元素的指针变量

    指针变量p是用“int *p;”定义的,它是指向整型数据的,p+1所指向的元素是p所指向元素的下一元素。

     1 #include <stdio.h>
     2 void main()
     3 {
     4     int a[3][4] = {{1,2,3,4},{5,6,7,8},{9,10,11,12}};
     5     int *p;
     6     for(p=a[0];p<a[0]+12;p++)
     7     {
     8         if((p-a[0])%4==0)
     9             printf("
    ");
    10         printf("%4d",*p);
    11     }
    12 
    13     printf("
    ");
    14 }
    View Code

    (2)指向由m个元素组成的一维数组的指针变量

    int( *p)[4] 表示p是一个指针变量,它指向包括4个整型元素的一维数组。注意圆括号不能省略,因为方括号的优先级高于*,因此p先与[4]结合

    ,p[4]是定义数组的形式,然后再与前面的*结合,*p[4]就是指针数组。

    int a[4];//a有4个元素,每个元素为整型
    int (*p)[4];

     1 #include <stdio.h>
     2 void main()
     3 {
     4     int a[3][4] = {{1,2,3,4},{5,6,7,8},{9,10,11,12}};
     5     int (*p)[4];
     6     int i,j;
     7     p = a;
     8     scanf("i=%d,j=%d",&i,&j);
     9     printf("a[%d,%d] = %d
    ",i,j,*(*(p+i)+j));
    10 }
    View Code

    4.3 用指向数组的指针作函数参数

    有两种方法:用指向变量的指针变量;用指向一维数组的指针变量。

    void func1(float *p, int n);
    void func2(float (*p)[4], int n);
    func1(*a, 12);
    func2(a,2);
  • 相关阅读:
    saltstack配置管理之YAML(二)
    自动化运维之saltstack 简单用法(一)
    异常处理,枚举,泛型
    面向对象二
    面向对象
    python面向对象
    方法(函数),内存空间,数组
    for循环,while循环,do while循环
    if判断,switch语句
    运算符
  • 原文地址:https://www.cnblogs.com/iambitiousman/p/3855048.html
Copyright © 2011-2022 走看看