C++ Primer第五版学习笔记十 引用与指针

引用:给对象起了一个另外的名字,引用必须初始化

引用不是对象,它只是给已经存在的对象起了一个别名,所以对引用的所有操作,都是在与之绑定的对象上进行的

因为引用不是对象,所以不能定义引用的引用

引用类型要跟与之绑定的对象类型严格匹配,且只能帮在对象上,不能与字面值或表达式绑在一起

#include <iostream>

int main()
{

    int i =0;
    int &refi = i; // 引用不是对象,它是为已经存在的对象起了另一个名字
    // int &refi2; // 编译报错,引用必须初始化
    std::cout << refi << std::endl; // 0

    refi = 2;
    std::cout << refi << std::endl; // 2

    i = 3;
    std::cout << refi << std::endl; // 3

    refi = 4;
    i = refi;
    std::cout << refi << std::endl; // 4

    int &refi3 = refi; // 引用不是对象,所以不能定义引用的引用,这个引用也是绑在i上面的
    refi3 = 5;
    std::cout << refi << std::endl; // 5

    double d = 3.14;
    // int &refd = d; // 编译报错,绑定的对象类型与引用的类型不一致
    // int &refi4 = 12;  // 编译报错,不能绑定到字面值上
    // int &refi5 = refi + i; // 编译报错,不能绑定到表达式上

    return 0;
}

指针:与引用类似,也实现了对其他对象的间接访问,存放的是某个对象的地址

指针与引用的不同:

1 指针本身是一个对象,允许对指针赋值或拷贝,在指针的生命周期里,它可以指向不同的对象

2 指针无需在定义时赋初值,如果没有初始化,将是一个不确定的值

指针的类型要与所指向的对象类型一致

利用指针访问对象,使用解引用符*

空指针:不指向任何对象 nullptr

void* 指针是特殊的指针类型,可用于存放任何对象的地址。但是对于该地址中存放的是什么类型的对象,并不知道。所以不能直接操作void*指针所指的对象

指针的指针:通过*的个数可以区分指针的级别,**表示指针的指针,***表示指针的指针的指针,以此类推

指向指针的引用:因为指针是对象,所以可以定义引用绑定到指针上

#include <iostream>

int main()
{

    int i =0;
    int *pi = &i; // &取地址符
    std::cout << i << std::endl;  // i的值
    std::cout << pi << std::endl; // i的地址
    std::cout << *pi << std::endl; // 访问指针所指向的对象,*解引用符
    *pi = 7;                       // 修改所指向对象的值
    std::cout << i << std::endl;
    std::cout << *pi << std::endl;

    double d = 3.14;
    double *pd1 = &d;
    // int *pd2 = &d;  // 编译错误,指针类型与指向的对象类型不一致

    int *pn1 = 0;       // 空指针
    int *pn2 = nullptr; // 空指针,推荐用法
    int *pn3 = NULL;    // 空指针,不推荐用法
    i = 0;
    // int *pn4 = i;       // 编译错误,把int变量赋给指针是错误的,即使这个变量的值是0

    void *pd3 = &d;
    // *pd3 = 3.15;  // 编译错误,void* 无法确认类型

    int val = 17;
    int *pval = &val;
    int **ppval = &pval; // 指针的指针
    std::cout << **ppval << std::endl;
    **ppval = 18;
    std::cout << **ppval << std::endl;

    int *&refpi = pi; // refpi是对指针pi的引用
    refpi = &val;
    *refpi = 19;
    std::cout << val << std::endl;
    std::cout << *refpi << std::endl;

    return 0;
}

变量的声明:

int* p1, p2;  // *修饰的是p1,并不作用于p2, 所以这句话,声明了一个指向int的指针(p1),声明了一个int型(p2)

猜你喜欢

转载自www.cnblogs.com/liyunfei0103/p/9100729.html