精华内容
下载资源
问答
  • 指针和引用有什么区别? 什么时候应该使用指针?什么时候应该使用引用? 01 指针和引用的区别 首先看一段代码: int a = 1; int b = 2; int *c = nullptr; c = &a; int &d = b; 指针其实就是...

    先抛出两个问题:

    • 指针和引用有什么区别

    • 什么时候应该使用指针?什么时候应该使用引用

    01 指针和引用的区别

     

    首先看一段代码:

    int a = 1;
    int b = 2;
    int *c = nullptr;
    c = &a;
    int &d = b;

    指针其实就是一个存放内存地址的整数,这个整数表示的是被指向的变量的地址。

    引用其实就是变量的别名,就是给变量重新起了一个名字,注意引用既然是个别名,那它一定要有本体,一个人叫王二小,我们也可以给它起个别名叫二蛋,我们提到二蛋和王二小其实都是同一个人。

    区别:

    • 指针在声明时可以暂时不初始化,即pointer = nullptr,指针在生命周期内随时都可能是空指针,所以在每次使用时都要做检查,防止出现空指针异常问题,而引用却不需要做检查,因为引用永远都不会为空,它一定有本体,一定得代表某个对象引用在创建的同时必须被初始化

    void FuncPtr(int *ptr) {  if (ptr != nullptr) {    cout << *ptr;  }}
    void FuncReference(int &ref) {    cout << ref;}
    
    • 指针存放的是地址,指针可以被重新赋值,可以在初始化时指向一个对象,在其它时刻也可以指向另一个对象,而引用非常专一,它会从一而终,它总是指向它最初代表的那个对象。再举个例子,有一个人叫特朗普,为他起个引用别名叫历史上最傻吊的总统,这个引用一定会从一而终,即无论什么时候,历史上最傻吊的总统一定是特朗普。而美国总统可以当作个指针,一段时间可以是奥巴马,过一段时间可以是特朗普,再过一段时间可能是nullptr。

     

    02 指针和引用的使用场景

     

    引用的主要功能就是作为函数的参数和返回值,看一段代码:

    struct A {    int a;};void func(const A &a) {    cout << a.a;}
    vector<int> vec(10);vec[3] = 3;

    为什么通过vec[3] =3可以改变vector容器的值,因为[]操作符返回的就是引用,相当于为内部的变量起了一个别名,这里还可以让[]操作符返回一个指针,即*vec[3]=3,这是不是有点丑,而且不符合语法需求。
     

    其实我们平时编程过程中可能也注意到,实际上引用可以做的事情指针都可以做,但为什么还要引用这个东西?

    答案:

    用恰当的工具做恰如其分的工作,指针可以毫无约束的操作内存中的任何东西,功能十分强大,但是也很危险,所以可以在恰当的时机使用引用,当你需要指向某个东西,而且一定专一,绝不会让其指向其它东西,例如有些函数参数为了避免拷贝可以使用引用,或者实现一个操作符而其语法需求无法由指针达成,例如vec[3]=3,可以使用引用,其它任何时候,都要使用指针。

     

     

    引用在c++11后其实有很多知识点,具体可以看我之前的文章:

    左值引用、右值引用、移动语义、完美转发,你知道的不知道的都在这里

    参考资料

    《More Effective C++》

    https://www.runoob.com/w3cnote/cpp-difference-between-pointers-and-references.html

    https://blog.csdn.net/weikangc/article/details/49762929

    https://www.jianshu.com/p/e548a978d737

    https://zhuanlan.zhihu.com/p/63096392

    展开全文
  • 引用使用场景 (一)给变量起别名 给变量起别名,顾名思义就像人也有别名一样,不管是别名还是原名都指的是同一个人,同样,下面声明b是a的别名,即ab的作用相同,都代表同一变量。int a; //定义 a 是整型变量...

        引用的使用场景 

        (一)给变量起别名

          给变量起别名,顾名思义就像人也有别名一样,不管是别名还是原名都指的是同一个人,同样,下面声明b是a的别名,即a和b的作用相同,都代表同一变量。

    int a;       //定义 a 是整型变量
    int &b = a;  //声明  b 是 a 的引用

          引用的三大特性:引用在定义时必须初始化、一个变量可以有多个引用、引用一旦引用其他一个实体,再不能引用其他实体。

          注: “ & ”为引用声明符,并不代表地址。

        (二)将引用作为函数的形参

          使用引用类型就不必再swap中声明形参是指针变量,指针变量要另外开辟内存单元,其内容是地址。而引用变量不是一个独立的变量,不单独占内存单元。而且在调用swap函数时,只需要传值即可,将引用作为函数的形参更加简单、直观、方便。

    void swap(int &a, int &b)
    {
        int temp;                                 //调用swap
        temp = a;                                 //int i = 3, j =5;
        a = b;                                    //swap(i,j);
        b = temp;
    }

        (三)将引用作为函数的返回值

          将引用作为函数的返回值,返回值的生命周期必须长于函数的生命周期,且不能反回栈空间上的引用。关于将引用作为函数返回值会存在的一些问题将在下次博客中详谈。

    int& Test(int& a)
    {
      a += 1;
      return a;
    }

        指针跟引用的区别

        相同点:引用类型的变量,在底层被当做指针来处理。
          区别:1、引用在定义时,必须初始化,但是指针没有要求,但建议初始化;

                     2、指针可以指向多个变量,引用类型一旦与变量绑定就不可更改;

                     3、定义一个指针变量 p 时,++p偏移一个元素类型的大小,而 int  a = 10;  int  &ra = a; ++ra则表示                        在a的实体上加1;

                     4、两者遇到sizeof的含义也不一样,指针的大小由平台和类型觉得,引用则取决于引用实体的大小;

                     5、指针需要手动寻址,引用通过编译器自动寻址。

        
    展开全文
  • 在设计函数时,应根据传入参数的值是否会被改变,来决定是使用引用形参还是指针形参。

    在设计函数时,应根据传入参数的值是否会被改变,来决定是使用引用形参还是指针形参。

    • 当传入的参数会被改变时,使用指针形参。
    • 当传入的参数不会被改变时,使用const修饰的引用形参。
    • 不应存在纯引用形参。

    以下示例来自LevelDB源码:

    // Open the database with the specified "name".
    // Stores a pointer to a heap-allocated database in *dbptr and returns
    // OK on success.
    // Stores nullptr in *dbptr and returns a non-OK status on error.
    // Caller should delete *dbptr when it is no longer needed.
    static Status Open(const Options& options, const std::string& name, DB** dbptr)
    {
        *dbptr = nullptr;
        DBImpl* impl = new DBImpl(options, dbname);
        ...
        if (s.ok()) {
        assert(impl->mem_ != nullptr);
        *dbptr = impl;
        } else {
            delete impl;
        }
        return s;
    }
    
    展开全文
  • 指针和引用

    2018-03-19 20:10:36
    1. 引用 引用不是定义一个新的变量,而是给一个已经定义的变量重新起一个别名。 格式为: 类型 &amp;amp; 引用变量名 = 已定义过的变量名; int a=10; int&amp;amp; b=a; 引用的特点: 一个变量可取多个...

    1. 引用


    引用不是定义一个新的变量,而是给一个已经定义的变量重新起一个别名。
    格式为: 类型 & 引用变量名 = 已定义过的变量名;

    int a=10;
    int& b=a;

    引用的特点:

    • 一个变量可取多个别名
    • 引用必须初始化
    • 引用只能在初始化的时候引用一次,不能改变为再引用其他的变量。

      示例:

    #include <iostream>
    using namespace std;
    
    int main()
    {
        int a = 10;
        int* p = &a;
        const int &b = a;
        a = 20;//a值改变b值也变
        //b = 30;//不能给常量(不能被修改的量)赋值
        const int c = 1;
        const int& d = c;
        //int& e = d;
        const int& f = 5;// 常量具有常性,只有常引用可以引用常量
    
        int i = 10;
        double s = 1.11;
        i = s;//数据丢失
        //int& s1 = s;//s是double,s1是int类型,赋值时生成临时变量,即s1引用的是具有常性的临时变量,所以不能赋值
    
        system("pause");
    }
    

    2. 引用的使用场景


    a. 引用作参数:

    void  Swap(int&  left, int&  right)//引用传递
    {
        int  temp = left;
        right = left;
        left = temp;
    }
    
    类似于指针传递。故当不希望函数内改变参数的值时,尽量使用常引用传参

    b. 传引用作为返回值

    #include <windows.h>
    #include <iostream>
    using namespace std;
    
    int&  Add(int  x, int  y) //传引用做返回值·
    // int Add  ( int x , int  y)//传值做返回值
    {
        int  ret = x + y;
        return  ret;
    }
    int main()
    {
        int  a = 3, b = 4;
        int  c = Add(a, b);
        cout << "c:" << c << endl;
        system("pause");
        return 0;
    }

    这里借助栈帧知识讲解:
    (关于栈帧查看之前的博客即可),截取了部分反汇编代码解释(vs2008):
    (1)传值返回值
    这里写图片描述
    (2)传引用
    这里写图片描述
    对比:传值时将ret的值放入eax寄存器中;传引用时将ret的地址放入eax寄存器中
    结论:

    (1)不要返回一个临时变量的引用。
    (2) 如果返回对象出了当前函数的作用域依旧存在,则最好使用引用返回,因为这样更高效。
    (3) 引用在语法上未开辟空间。

    3. 引用和指针的区别和联系


    (笔试易考)

     1 . 引用只能在定义时初始化一次,之后不能改变指向其它变量(从一而终);指针变量的值可变。
     2 . 引用必须指向有效的变量,指针可以为空。
     3 . sizeof指针对象和引用对象的意义不一样。sizeof引用得到的是所指向的变量的大小,而sizeof指针是对象地址的大小。
     4 . 指针和引用自增(+ + )自减(- - )意义不一样。
     5 . 相对而言,引用比指针更安全。
    
    展开全文
  • 指针和引用什么时候用?

    千次阅读 2017-09-28 07:55:21
    通常情况下是根据不同场景来选择是使用指针还是引用,选择适合场景需求的才是一个优秀程序员所应具备的能力。 我们在做项目开发时,也会考虑到一个维护成本,如果你的前任是一个“高手”,写的代码你基本看不懂,无...
  • 指针和引用区别笔记

    2014-08-30 14:58:18
    指针是指向一个指定类型变量的地址值; 引用是一个指定类型变量的别名,主要用于函数参数返回值类型; 引用不可为空,但指针可以,指针是一个变量可以随意赋值,但引用是一个指定类型变量的...使用场景: 若你
  • 笔者介绍:姜雪伟,IT公司技术合伙人,IT高级讲师,CSDN社区专家,特邀...CSDN视频网址:http://edu.csdn.net/lecturer/144 CC ++支持与大多数其他编程语言不同的指针, 其他语言包括C ++,Java,Python,Ruby,Per
  • 引用(hard reference),也叫指针
  • 使用引用 C++四种常用智能指针 unique_ptr(局限性较大) shared_ptr weak_ptr经常联合在一起用 weak_ptr auto_ptr(C++11已经废弃,C++17中正是删除) deprecated 目前还能用,不久的将来将不支持。 从应用方面...
  • 文章目录指针和动态内存分配引用&将引用用于结构何时使用引用参数?指针指针和const通过指针返回字符串的函数通过指针返回结构函数指针声明函数指针函数指针用武之地关于指针的一些思考结构体调试链表初识链表...
  • 1.如果一个指针所指向的对象,需要用分支语句加以确定,或者在中途需要改变他所指的对象,那么在它初始化之后需要为他...3.使用函数指针,由于没有函数引用,所以函数指针无法被引用替代。 4.使用new创建的对象或数
  • rust指针引用、智能指针

    千次阅读 2020-06-15 15:49:19
    文章目录指针引用可变引用不可变引用悬垂引用引用&借用解引用智能指针 指针 指针是个通用概念,它表示内存地址这种类型,其引用或“指向”其他数据。Rust中的指针是“第一类公民”(first-class values),可以...
  • c++基础——区分引用和指针

    多人点赞 热门讨论 2021-08-18 00:22:28
    1.4引用使用场景 2.指针 2.1概念 2.2获取对象的地址 2.3利用指针访问对象 2.3空指针 2.4野指针 2.4.1概念: 2.4.2野指针的产生: 2.5各个指针类型的含义 2.6 void* 指针 2.7指向指针指针 ​ 2.8...
  •   引用(referene)是一种复合类型,即基于其他数据类型的类型(指针亦是一种复合类型)。引用实质是给变量起了一个别名,而不是一个实体的类型,所以编译器不会给引用分配内存。同时,对引用的操作等效于对原变量...
  • weak_ptr:弱指针shared_ptr共享指针是绑定的,只是不统计入引用计数而已。意思是如果有就用一下,如果没有,也没有关系。所以有些场景,我们几乎可以确定shared_ptr是肯定不会释放的,所以想用shared_ptr.get()...
  • 原文地址:Rust 中几个智能指针的异同与使用场景想必写过 C 的程序员对指针都会有一种复杂的情感,与内存相处的过程中可以说是成也指针,败也指针。一不小心又越界访问了,一不小心又读到了内...
  • 在正式开始介绍多维指针和多维数组之前,笔者要先介绍一些关于数组下标引用和指针访问的相关内容。了解这些内容,会更加有助于我们理解后面的多维指针和多维数组。 1.以下标引用的方式访问数组 在使用数组的场合...
  • C++中的指针引用和Java中的对象引用 一、C++中指针和引用的区别 相同点:在c++中,指针和引用都可以让人间接地操作一个对象。 不同点:首先说两者在定义上的区别,指针是存放对象的地址的一块内存,而引用是...
  • 智能指针引用计数详解(一)

    千次阅读 2018-12-10 22:25:38
    在《C++Primer》书13.5章 提到了该技术的具体使用场景和实现。通过反复阅读代码测试终于了解其中的思想,下面谈谈自己的理解,如果发现有什么问题,请大家批评指正。 什么是智能指针? 智能指针其实就是一个类,...
  • C++ 最常见的显示使用this 指针场景

    千次阅读 2015-11-15 00:30:57
    有一种场景必须显示使用this指针,需要将一个对象整体引用而不是引用对象的一个成员时。最常见的情况是在成员函数中使用this,返回对调用该函数的对象的引用。 #include #include #include #include #include ...
  • 文章目录复合类型引用概念与使用引用的定义注意指针概念声明方式取地址符指针值空指针利用指针访问对象赋值和指针void* 指针指向指针指针指向指针引用初始化所有指针有多重含义的某些符号const限定符 ...
  • JNI 引用, DeleteLocalRef使用场景详解

    千次阅读 2020-06-22 15:18:18
    局部引用: ... (在循环体或回调函数中)创建大量 JNI 局部引用,即使它们并不会被同时使用,因为 JVM 需要足够的空间去跟踪所有的 JNI 引用,所以可能会造成内存溢出或者栈溢出; 如果对一...
  • 当函数的内部创建一个智能指针,并需要在函数外使用时,此时,函数的返回值必须为该智能指针类型(即函数内创建的智能指针退出该函数时,引用计数不会-1),否则,当函数体执行结束时,该智能指针引用计数...
  • 引用和指针的差别?

    2015-08-25 10:00:04
    1:非空区别,在任何情况下都不能使用指向空值的引用。一个引用必须总是指向某些对象。所以如果你使用一个变量并让它指向一个对象,但是该变量在某些时候也可能不指向任何对象,这时应该将这个变量声明为指针,这样...
  • 转载自 weak_ptr也是一个引用计数型智能指针,但是它不增加对象的引用计数,即弱引用。与之相对,shared_ptr是强引用,只要有一...有两个指针p1p2,指向堆上的同一个对象Object,p1p2位于不同的线程中。假设线程..
  • 函数返回局部变量的指针引用

    千次阅读 2018-05-16 23:17:53
    一般来说,由于在离开函数后局部变量会被释放,所以是不允许函数返回指向局部变量的指针引用的。我们往往需要遵循如下原则:引用作为返回值,必须遵守以下规则:(1)不能返回局部变量的引用。主要原因是局部变量...
  • 引用 概念(贴标签式) 引用不是新定义一个变量,而是给已存在变量取了一个别名...使用场景 1.作为函数形参 2.作为函数返回值 注意事项 a. 引用在定义时必须初始化 b. 一个变量可以有多个引...
  • 【C++】weak_ptr弱引用智能指针详解

    千次阅读 多人点赞 2020-05-03 15:34:11
    相比于上一代的智能指针auto_ptr来说,新进老大shared_ptr可以说近乎完美,但是通过引用计数实现的它,虽然解决了指针独占的问题,但也引来了引用成环的问题,这种问题靠它自己是没办法解决的,所以在C++11的时候将...
  • (一)基本用法 不通过函数名调用函数 #include <stdio.h> void printInt(int n);...//给返回值为void 参数为一个int的函数指针重命名,命名为pFunc_t ...//如果没有重命名,不可以使用此句,应该为:vo...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 83,521
精华内容 33,408
关键字:

指针和引用的使用场景