C++ 新特性

内联函数(inline)

image.png

image.png

内联函数其实是声明,只能放在头文件里,不能放在实现(定义)里。
类在头文件里声明函数时直接写上body,那么这个函数其实就是inline的
如果要在类中指明一个函数时inline的,只需要在头文件中函数声明的下面直接写上其实现,如下:

image.png

引用

image.png
    int a = 5;
    int c = 6;
    int &b = a;//将引用与变量关联起来
    b = c;
    cout << a << "\t" << b << endl;

输出的日志如下:
6 6
所以这也验证了引用一旦被关联就将一直效忠于它。

不可用直接引用常量(字面量)

double& d = 12.3;//错误
d=111;//违背了常量的基本概念
const  double& d = 12.3;//正确

原理:因为引用是别名,所以当引用就赋值为常量以后,那就意味着引用不能被重新赋值,这就违背了引用的定义。所以引用不允许在初始化时赋值常量。如果非要在初始化时赋值常量可以在引用前添加const关键字,表示这是一个不可变引用。

注意:当我们对引用进行重新赋值时,也会改变初始化变量的值。

引用参数

void swap1(int, int);//普通
void swap2(int *, int *);//指针
void swap3(int &, int &);//引用

int main() {

    int a = 10, b = 5;
    cout << "a和b的内存地址:" << &a << "\t" << &b << endl;
    cout << "\n"<<endl;
    swap1(a, b);
    cout << "执行swap1后的a b的值:" << a << "\t" << b << endl;
    cout << "\n"<<endl;
    swap2(&a, &b);
    cout << "执行swap2后的a b的值:" << a << "\t" << b << endl;
    cout << "\n"<<endl;
    swap3(a, b);
    cout << "执行swap3后的a b的值:" << a << "\t" << b << endl;

    return 0;
}

//复制拷贝变量值 不会影响原来的值
void swap1(int num1, int num2) {
    cout << "num1和num2的内存地址:" << &num1 << "\t" << &num2 << endl;
    int temp;
    temp = num1;
    num1 = num2;
    num2 = temp;
}

//复制拷贝变量地址,对地址内的值进行交换会改变原来的值
void swap2(int *p1, int *p2) {
    cout << "p1和p2的内存地址:" << &p1 << "\t" << &p2 << endl;
    cout << "p1和p2的值:" << p1 << "\t" << p2 << endl;
    int temp;
    temp = *p1;
    *p1 = *p2;
    *p2 = temp;
}

//复制拷贝变量本身,即内存地址也一致,其实是指针的高级实现
void swap3(int &ref1, int &ref2) {
    cout << "ref1和ref2的内存地址:" << &ref1 << "\t" << &ref2 << endl;
    cout << "ref1和ref2的值:" << ref1 << "\t" << ref2 << endl;
    int temp;
    temp = ref1;
    ref1 = ref2;
    ref2 = temp;
}

输出日志如下:

a和b的内存地址:0x61ff0c 0x61ff08


num1和num2的内存地址:0x61fef0   0x61fef4
执行swap1后的a b的值:10        5


p1和p2的内存地址:0x61fef0       0x61fef4
p1和p2的值:0x61ff0c     0x61ff08
执行swap2后的a b的值:5 10


ref1和ref2的内存地址:0x61ff0c   0x61ff08
ref1和ref2的值:5        10
执行swap3后的a b的值:10        5

换一种方式理解函数传参:

下面我说的其实针对任何编程语言都是适用的。如果你对内存结构有过了解的话就会知道,我们的函数其实运行在虚拟机栈中,每个函数其实就是一个栈桢,当我们调用函数的时候,栈桢会入栈,函数执行完出栈。在函数中定义的变量都是临时变量,生命周期就是函数的执行周期。了解这些之后,我们再来看方法调用传参就会有一种新的理解。首先我们在函数中定义的形参它也是属于临时变量,所以他在函数中定义的临时变量唯一的不同点事不需要我们手动去初始化,因为在函数调用的时候它已经被初始化过了,还有一点,那就是其实所有的函数调用都是变量传值函数调用。所以我们来看一下上面的三个例子:

1.普通变量函数调用:我们将变量的值拷贝一份,保存在栈桢中并赋值给了临时变量,所以当我们对临时变量进行任何的操作其实都不会影响外部变量的值。

2.指针变量函数调用:我将变量的内存地址拷贝一份,保存在栈中并赋值给了指针,所以当我们对指针所指向的内存空间进行操作时也就影响了所有指向同一内存空间的变量。

3.引用变量函数调用(传指针的语法糖):我们传引用的时候比较特殊,无论你传值还是传指针,函数都会生成一个临时变量,但传引用时,不会生成临时变量,你可以把引用当做语法糖,但传引用主要是它不生成临时变量,不进行返回值copy等,速度快。实际上,你也可以把引用看做是通过一个常量指针来实现的,它只能绑定到初始化它的对象上

参数默认值

image.png
image.png

函数模板

image.png

面向对象

image.png

image.png

C++对象创建

image.png

1.创建头文件
hero.h

#ifndef DEMO_HERO_H
#define DEMO_HERO_H
#include <string>
#include <iostream>
using namespace std;

class Hero {
private:
    string name;

public:
    Hero();
    const string &getName() const;
    void setName(const string &name);
    void attack();
};

#endif //DEMO_HERO_H

2.创建实现文件
hero.cpp

#include "Hero.h"

Hero::Hero() {

}

void Hero::attack() {
    cout << "ssss" << endl;
}

const string &Hero::getName() const {
    return name;
}

void Hero::setName(const string &name) {
    Hero::name = name;
}

3.对象创建和调用
main.cpp

#include "Hero.h"
int main() {
    Hero hero;
    hero.attack();
    hero.setName("66666");
    cout << "姓名是:" << hero.getName() << endl;
    return 0;
}

构造函数

image.png

带参构造函数

image.png

创建对象的2中方式:

Student s1;//栈中分配内存 栈内存容量有限 一般不推荐使用
Student s2 = new Student(); //堆内存中分配内存 当对象不再使用时 要及时释放内存 delete s2

析构函数

image.png

this指针

image.png

image.png

const

image.png

const如果位于前面则对象是const,位于后面则指针是const。**
实例:

char *s中的s是指针,而指针是指向一块内存区域,它指向的内存区域的大小可以随时改变,而且当指针指向常量字符串时,它的内容是不可以被修改的,否则在运行时会报错。
char s[]中的s是数组首地址,而数组首地址对应着一块内存区域,其地址和容量在生命期里不会改变,只有数组的内容可以改变。

深入 char * ,char ** ,char a[ ] ,char *a[] 内核
注意:C语言中操作字符串是通过它在内存中的存储单元的首地址进行的,这是字符串的终极本质

int main() {
    //指针数组 []的优先级高于* 所以 他是一个数组,然后数组中保存的类型是char *
    char *array[] = {"aaa", "bbb", "ccc"};
    cout << sizeof(array) << endl; // 12 因为array是数组 保存的是指针 所以长度为3*4=12;
    char **ptr_array = array;
    cout << ptr_array << "\t" << *ptr_array << endl;

    int a = 1, b = 2, c = 3;

    int *iarray[] = {&a, &b, &c};
    int **ptr_iarray = iarray;
    cout << ptr_iarray << "\t" << *ptr_iarray << "\t" << **(++ptr_iarray) << endl;
    return 0;
}

log:

12
0x63fefc aaa
0x63fee8 0x63fef4 2

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 194,491评论 5 459
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 81,856评论 2 371
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 141,745评论 0 319
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 52,196评论 1 263
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 61,073评论 4 355
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 46,112评论 1 272
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 36,531评论 3 381
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 35,215评论 0 253
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 39,485评论 1 290
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 34,578评论 2 309
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 36,356评论 1 326
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 32,215评论 3 312
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 37,583评论 3 299
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 28,898评论 0 17
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 30,174评论 1 250
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 41,497评论 2 341
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 40,697评论 2 335

推荐阅读更多精彩内容