zoukankan      html  css  js  c++  java
  • 2019年7月11日星期四(C语言)

    一、复杂指针定义

    1、简单指针   -> 指向基本数据类型  char int long..

        复杂指针   -> 指向非基本数据类型  指针/数组/函数/结构体

    2、二级指针?

    指向指针的指针。

    int a;

    int *pa = &a;   pa就是一级指针

    int **p = &pa;  p就是二级指针

    3、数组指针?

    指向整个数组的基地址指针就是“数组指针”

    1)如何定义数组指针?

    方法与定义简单指针一致。

    int a;

    int *p = NULL;

    p = &a;  -> 整型指针   -> 指针类型:int*   -> 代表该指针指向一个整型数据。

    int A[3];

    int(*p)[3] = &A;  -> 数组指针  -> 指针类型:int(*)[3]   -> 代表该指针指向一个具有3个int类型数据的数组

    2)数组中&AA有什么区别?

    &A  -> 代表这个数组的地址        int(*)[3]

    A   -> 代表这个数组首元素的地址  int *

    int A[3];

    int(*p)[3]=A;   -> 不能把int*类型数据赋值给int(*)[3],因为类型不匹配!

    3)解引用

    int A[3] = {100,200,300};

    int(*p)[3] = NULL;

    p=&A;

    请问*p得到什么?

    *p = *(&A) = A = &A[0]  -> 解引用数组指针,得到数组首元素的地址。

    请问p[0]/p[1]是什么?

    p[0] = *(p+0) = *(p) = *(&A) = A = &A[0]

    p[1] = *(p+1)  p+1已经越界,访问未知区域。

    请问(*p)[1]得到什么?

    (*p)[1] = (*&A)[1] = A[1] = 200

    练习1:若有以下说明:

    int B[10];

    int (*p)[10]=&B;

    int *px=B;

    则下列能正确引用数组的元素的是?

    A. *p+1  B.*(p[1])  C.(px+3)[2]  D.(*px)[3]  E. (*p)[0]  F. *(px+1)

    4、函数指针?

    指向函数的一个指针。

    1)如何定义函数指针?

    例子:

    int a;

    int *p = &a;

    int fun(int x,int y);   -> 指向该函数指针怎么写?

    int(*p)(int,int) = &fun;

    结果:int(*p)(int,int)

    变量名:p

    数据类型:int(*)(int,int)

    2)在linux C语言中,函数名字就是函数的地址,所以:  fun 等价于 &fun

    int fun(int x,int y); 

    int(*p)(int,int) = &fun;  等价于   int(*p)(int,int) = fun;

    练习2:求出两个数字最大值,要求使用函数指针完成。

    #include <stdio.h>

    int fun(int x,int y)

    {

           int z;

           z = (x > y ? x : y);

           return z;

    }

    int main()

    {

           int max;

           int(*p)(int,int) = NULL;

           p = &fun;

           max = p(100,200);

           printf("max = %d ",max);

           return 0;

    }

    二、数组作为函数的参数时,在内存中的变化情况?

    1、学习过传递类型

    例子1:传递int类型数

    void fun(int x)  //x = a;

    fun(a);

    例子2:传递指针地址

    void fun(int *x)  x = &a;

    fun(&a);

    例子3:传递函数

    void fun(void (*x)(int))  x = &myfun  /  x = my_fun

    void my_fun(int a);

    fun(my_fun);

    2、数组作为实参时,其实将数组首元素传递过去。

    例子:

    以下三种写法完全等价

    void fun(int x[])   // x = A = &A[0]

    void fun(int x[3])  // x = A = &A[0]

    void fun(int *x)    // x = A = &A[0]

    int main()

    {

           int A[3];

           fun(A);  //在这里,A不是作用sizeof(),所以代表首元素地址  int*

           //等价于fun(&A[0]);

    }

    练习:

    10、有以下程序

    void swap1(int c0[], int c1[])

               int t ;

           t=c0[0]; c0[0]=c1[0]; c1[0]=t;

    }

     

    void swap2(int *c0, int *c1)

           int t;

           t=*c0; *c0=*c1; *c1=t;

    }

    main()

    {

           int a[2]={3,5}, b[2]={3,5};

           swap1(a, a+1);

           swap2(&b[0], &b[1]);

           printf(“%d %d %d %d ”,a[0],a[1],b[0],b[1]);

    }

    程序运行后的输出结果是( D )

    A)3 5 5 3       B)5 3 3 5

    C)3 5 3 5       D)5 3 5 3

    9、有以下程序

    void fun(int *a,int i,int j)

           int t;

               if(i<j)

           {

                  t=a[i];

                  a[i]=a[j];

                  a[j]=t;

                  fun(a,++i,--j);

           }

    }

    main()

    {  

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

               fun(a,0,5);

               for(i=0;i<6;i++) 

                  printf(“%d”,a[i]);

    执行后的输出结果是( A )

    A) 6 5 4 3 2 1       B) 4 3 2 1 5 6

    C) 4 5 6 1 2 3       D) 1 2 3 4 5 6

    三、数组作为函数的返回值时,情况是如何的?

    #include <stdio.h>

    char *fun()

    {

           char A[4] = {'a','b','c'};

           printf("A = %p ",A);

           printf("%s ",A);

           return A;   //-> 返回数组首元素的地址  类型: char*

    }

    int main()

    {

           char *p = NULL;

           p = fun();

           printf("p = %p ",p);

           printf("%s ",p);

    }

    编译警告:warning: function returns address of local variable  -> 数组A再函数fun结束时,内存空间会释放。

    解决方案:

    1)将数组设置为全局变量

    2)在数组前面加static修饰数组   -> 数组被static修饰后,不再存在与栈区,而是存在数据段。

    四、二维数组

    1、二维数组的基本概念

    二维数组在内存中是线性规则,不存在行与列的关系,其实二维数组就是一个一维数组,只是一维数组中每一个成员都是数组。

    例子:

    整型数组: int A[5]  -> 该数组中每一个成员都是int类型数据。

    二维数组: 数组 A[5] -> 该数组中每一个成员都是数组

    2、如何定义二维数组?

    只需要确定数组的元素个数与每一个元素的数据类型即可!

    定义数组的方式:

    例子1:定义具有5int类型数据的数组:

    1)给一个数组名 A

    2)确定数组中元素的个数,使用[]括住它,跟在数组名后面 A[5]

    3)确定数组中每一个成员的数据类型是什么  int a;

    4)将第3步结果的变量名去掉  int

    5)将第4步结果写在第2步结果前面  int A[5]

    例子2:定义二维数组

    1)给一个数组名 B

    2)确定数组中元素的个数,使用[]括住它,跟在数组名后面 B[2]

    3)确定数组中每一个成员的数据类型是什么  int A[3]

    4)将第3步结果的变量名去掉  int [3]

    5) 将第4步结果结合到第2步结果中   int B[2][3]

     

    结果:int B[2][3]

    代表这个数组中有两个成员,每一个成员都是具有3个int类型数据的数组。

    3、二维数组的赋值

    int B[2][3] = {{1,2,3},{4,5,6}};

    4、二维数组的数组名

    例子:int B[2][3]

    sizeof(B) = 24

    &B            -> 代表整个二维数组的地址,              类型: int(*)[2][3]

    B=&B[0]       -> 代表二维数组的首元素的地址,          类型: int(*)[3]

    B[0]=&B[0][0] -> 代表二维数组的首元素的首元素的地址,   类型: int *

    B[0][0]       -> 代表二维数组的首元素的首元素的值,     类型: int

    5、解引用

    1)请问解引用二维数组的名字得到什么?

    得到二维数组的首元素的首元素的地址。

    int B[2][3] = {{1,2,3},{4,5,6}};

    *B=*(&B[0])=B[0]=&B[0][0]

    2)请问解引用二维数组的首元素得到什么?

    得到二维数组的首元素的首元素的值。

    *B[0]=*(&B[0][0])=B[0][0]

    练习2:

    12、若有以下说明和语句:int c[4][5],(*p)[5];p=c;能正确引用c数组元素的是( D )

    A) p+1    B) *(p+3)    C) *(p+1)+3    D) *(p[0]+2)

    13、有以下程序

    main()

    {  

           int a[3][3],*p,i;

            p=&a[0][0];

            for(i=0;i<9;i++) 

                  p[i]=i+1;

            printf(“%d ”,a[1][2]);

    }

    程序执行以后的输出结果是( B )

    A) 3     B) 6     C) 9     D) 7

  • 相关阅读:
    Python
    Python
    Python
    Python
    Python
    Python
    Scala核心编程_第01章_Scala概述
    与富婆讨论性,死亡与生活的意义
    python邮件发送给多人时,只有第一个人能收到的问题
    少年维特的烦恼
  • 原文地址:https://www.cnblogs.com/zjlbk/p/11172159.html
Copyright © 2011-2022 走看看