zoukankan      html  css  js  c++  java
  • 指针

    指针

    一.认识指针/为什么要学习指针

      [需求]编写自定义函数func,将main函数中的两个整形变量的值交换  

    void func(int a,int b)
    {
        //交换传进来的a,b的值
        int temp=a;
        a=b;
        b=temp;
    }
    int main(int argc, const char * argv[])
    {
        int a=10,b=20;
        func(a,b);
        printf("%d %d
    ",a,b);//10 20
        return 0;
    }

      [注]指针是为了帮助我们实现跨内存访问

    二.指针的定义

      类型符*指针变量名;

      例子:int *i;

      [注]指针变量中存的是地址

    三.指针的初始化

      [注]刚定义出来的指针变量,如果不进行初始化,指针变量的值是不确定的,我们称这样的指针为“野指针

        int a;
        int *i = &a;//这里是定义一个指针变量i,同时给i赋值为&a
                    //一旦指针变量i中存有一个地址,i就指向了a
        //一旦指针变量i指向了普通变量a,就可以通过i来访问a中的数据
        *i    //取出i指向的a中的数据
        *i = 20 //改变i指向的a中的数据

    四.指针的赋值

        int a,b;
        int *ppi = &a;    //ppi指向了a
        ppi = &b;          //ppi指向了b

      [注]指针变量的赋值,是为了改变指针变量的指向

      [注]通过对指针变量取*,可以访问指针变量所指向的内存单元的数据,所访问数据的内存单元大小是由指针本身的类型决定的

    五.指针变量所占内存大小

        int *p1;
        char *p2;
        double *p3;
        printf("%ld
    ",sizeof(p1));//8
        printf("%ld
    ",sizeof(p2));//8
        printf("%ld
    ",sizeof(p3));//8
        //在64位系统下,不同类型的指针变量占8字节内存
        //在32位系统下,不同类型的指针变量占4字节内存

    六.指针和函数——指针变量要作为函数的参数

      [指针作为函数参数]如果需要在一个函数中访问另一个函数中的数据,这是就需要使用指针(传入数据的地址,用一个指针变量接收)

    void foo(int *a)//a=&b
    {
        printf("%d
    ",*a);
        *a=20;
    }
    
    void main(void)
    {
        int b;
        foo(&b);
    }

    七.指针和数组

      <1>指针加1

        [注] 指针变量加1,实际是加了指针变量的类型所对应字节数

      <2>指针和数组的关系

        int a[10]={1,2,3,4,5,6,7,8,9,10};
        int *p;//这是个野指针
        p=a;//一旦数组名赋值给指针变量,指针变量就可以当数组名使用(指针变量中存的是数组首元素的地址)
        //数组名,代表数组中首元素的地址
        //a==&a[0]

        数组传参,数组名作为参数传参,需要通过指针变量接收

      [数组传参]

        <1>数组传参,可以用一个指针变量接收

          void pri(int *p)

        <2>数组传参,也可以用一个数组接收,但是在函数内部,数组名会立即退化成指针变量

          void pri2(int ap[100])//参数部分,数组大小没意义

          int ap[100] 可以理解成 int *ap

        [注] 以上两种接收方式,都无法知晓数组中元素的个数,必须在传入数组名的同时传入数组元素的个数

           void pri(int *p,int n)

          void pri2(int ap[],int n)

         [注] 在函数中返回一个数组名,需要用指针类型的返回值类型 

          例如:返回一个 int a[10];

    int * fun(void)
    {
        int a[10];
        return a;
    }

     

    八.const关键字修饰指针

      const关键字可以修饰变量(普通变量,指针变量)

      const修饰普通变量,被修饰的普通变量 就变为常量(不能直接通过赋值语句修改变量的值)

        int const a;//a成了常量
        const int a;//a成了常量
        a=10;////const修饰的普通变量,变为“只读”变量
        const修饰指针变量,被修饰的指针变量有两种情况
        int *const pi;(锁定的是地址)//因为const直接修饰的是pi,所以pi不能变,但是*pi可以变
        pi=&b;//
        *pi=100;//
        int const * pi;(锁定的是值)//因为const直接修饰*pi,所以*pi不能变,但是pi可以变 

     

    九.高级指针用法

      <1>数组指针

        int (*arr)[4];
        //这是一个数组指针,指针名为arr,用来指向一个数组(int[4])
        //数组首元素的地址&array[0]或者array
        //数组的首地址&array
        arr=&array;

        [] 数组指针常和二维数组配合使用

      <2>指针数组

        //用来批量定义指针变量
        int *arr[4];
        //这是一个数指针数组,数组名为arr,数组arr具有4个元素,每个元素是一个指针变量(int*)
        //arr[0],arr[1],arr[2],arr[3]

      <3>函数指针

        [] 函数指针,本质还是一个指针,是用来指向一个函数的指针 

        //定义一个函数指针
        int (*p)(int);
        //这是一个指针变量p,用来指向一个函数,这个函数必须是返回值类型为int,带有一个int参数的函数
        p=foo;//将函数foo的首地址存入函数指针变量p中
        //使用p调用存储在p中的函数
        p(10);

        [需求] 保存10个函数的首地址,需要定义函数指针数组

        int (*p)(int)[10];
        p[0]=foo;
        p[1]=func;
        ......

      <4>二级指针

        int ** pp;//定义了一个二级指针pp,用来指向一个一级指针的
        //[需求]--[访问]一级指针变量所在内存单元的数据
        //需要使用 二级指针pp来访问一级指针变量p的数据
        // 可以使用二级指针变量 改变 一级指针变量 中存的地址(oc中会用到)
        int a=10;
        int *p=&a;
        pp=&p;//二级指针变量pp指向一级指针变量p
        *pp=&b;//通过二级指针变量pp修改 所指向的一级指针变量p 中存的地址(让一级指针变量p指向变量b)

    [拓展题]

      编写函数,传入一个字符数组,返回数组中第一个出现的字母,如果字符中没有字母,返回0.

    //返回值是char类型
    #include <stdio.h>
    char app(char *p,int n);
    char app(char *p,int n)
    {
        char m='0';
        for (int i=0; i<n; i++)
        {
            if (p[i]>='a'&&p[i]<='z')
            {
                m=p[i];
                break;
            }
        }
        return m;
    }
    
    int main(int argc, const char * argv[])
    {
        char a[10];
        for (int i=0; i<10; i++)
        {
            scanf("%c",&a[i]);
        }
        char n=app(a, 10);
        printf("%c
    ",n);
        return 0;
    }

     

  • 相关阅读:
    oracle内核参数详解
    oracle分区表原理学习
    expdp导出时报错ora-16000
    【CS224n-2019学习笔记】Lecture 1: Introduction and Word Vectors
    【SQL必知必会笔记(3)】SELECT语句的WHERE子句数据过滤操作
    【SQL必知必会笔记(2)】检索数据、排序检索数据
    【SQL必知必会笔记(1)】数据库基础、SQL、MySQL8.0.16下数据库、表的创建及数据插入
    win10,64位操作系统安装mysql-8.0.16经验总结(图文详细,保证一次安装成功)
    【机器学习实战笔记(3-3)】关于朴素贝叶斯实现代码中的一些错误总结
    【机器学习实战笔记(3-2)】朴素贝叶斯法及应用的python实现
  • 原文地址:https://www.cnblogs.com/firstsky/p/5892023.html
Copyright © 2011-2022 走看看