C++说爱你不容易-2

C++软件与嵌入式软件面经解析大全(蒋豆芽的秋招打怪之旅)


本章讲解点

  • 1.1 C++与C的区别——看看你的理解是否深刻
  • 1.2 从代码到可执行文件的过程
  • 1.3 extern "C"
  • 1.4 宏——到底是什么
  • 1.5 内联函数
  • 1.6 条件编译
  • 1.7 字节对齐详解
  • 1.8 Const——今天必须把它搞懂
  • 1.9 Static作用
  • 1.10 volatile和mutable
  • 1.11 volatile在嵌入式里的应用
  • 1.12 原子操作
  • 1.13 指针与引用的区别
  • 1.14 右值引用
  • 1.15 面向对象的编程思想
  • 1.16 类
  • 1.17 类的成员
  • 1.18 友元函数
  • 1.19 初始化列表
  • 1.20 this指针
  • 1.21 继承
  • 1.22 多态
  • 1.23 虚函数与重写
  • 1.24 虚构造函数与虚析构函数
  • 1.25 函数重载
  • 1.26 操作符重载
  • 1.27 迭代器与指针
  • 1.28 模板
  • 1.29 C++智能指针
  • 1.30 四种cast转换
  • 1.31 Lambda
  • 1.32 function和bind

受众:本教程适合于C/C++已经入门的学生或人士,有一定的编程基础。

本教程适合于互联网嵌入式软件求职的学生或人士。

img

故事背景

img

蒋 豆 芽:小名豆芽,芳龄十八,蜀中人氏。卑微小硕一枚,科研领域苟延残喘,研究的是如何炒好一盘豆芽。与大多数人一样,学习道路永无止境,间歇性踌躇满志,持续性混吃等死。会点编程,对了,是面对对象的那种。不知不觉研二到找工作的时候了,同时还在忙论文,豆芽都秃了,不过豆芽也没头发啊。

隔壁老李:大名老李,蒋豆芽的好朋友,技术高手,代码女神。给了蒋豆芽不少的人生指导意见。

导 师:蒋豆芽的老板,研究的课题是每天对豆芽嘘寒问暖。

img

故事引入

img

“中国土豆科技大学一研三学生因论文压力太大,跳楼轻生,家长指责导师故意延毕。”豆芽将这条新闻推送到了微信朋友圈,并配文:默哀。我也压力好大啊。


导 师:(试探)豆芽,你这实验尽力做就行了,你也别压力大,慢慢来嘛。

蒋 豆 芽:老师,我压力好大啊,也想把实验做出来,不然辜负了您的一片谆谆教导。

导 师:不用压力大,周末好好休息下,实验慢慢做就行了。

蒋 豆 芽:好的!(豆芽脸上笑嘻嘻,心里小感动,老师蛮好的。实验要继续加油!)


蒋 豆 芽:(吹着口哨)我得儿意的笑,我得儿意的笑。。。。。。

隔壁老李:哟,豆芽,什么事啊这么开心,不用搞实验了?

蒋 豆 芽:别介,老李。我回顾你上次跟我讲的宏,在C++中,尽量使用const去替代非参数宏命令,这样大大增强我们程序的健壮性。我今天在思考,const是什么样的机制呢,为什么可以做到不变?还有,const有哪些应用场景呢?

隔壁老李:(啧啧啧)哟,芽别三日,当刮目相待啊,开始学会思考知识点了,没错,找工作中,面试只是一个过程,这不仅仅是应试,学知识不是应付找工作,而是真正提升自己的技术能力,学会思考知识点背后的原理,掌握知识点的核心,才是找工作给予我们的最大的启示。(语重心长)凭这一点,豆芽,你成熟了,不枉为父谆谆教导。

蒋 豆 芽:老李,说话就说话,别占我便宜好吗?

隔壁老李:(嘿)哈哈。哦?不想听啊,不想听算了呗。

蒋 豆 芽:爸爸!

隔壁老李:哈哈,好啦,跟你开玩笑的。今天我们先来聊聊const,说const之前,我们要先说说常量,什么是常量呢?

常量是一种标识符,它的值在运行期间恒定不变。C语言和C++中都可以用#define来定义常量(称宏常量)。除此之外,C++语言还可以用const来定义常量(称const常量),就是我们今天要说到的主角了。那么豆芽我问问你,我们为什么需要常量?

蒋 豆 芽:这个我还真没想过,我只知道有这个东西,但为什么要用就不知道了。

隔壁老李:(语重心长)所以我们的学习不能仅仅停留在这个地步,不仅要知其然,还要知其所以然,凡事多问几个为什么,就会引申出很多的知识。

蒋 豆 芽:老李,我发现你越来越像我高中班主任了。

隔壁老李:(好奇)哦?是讲解细致入微?

蒋 豆 芽:不,是啰里啰嗦了。

隔壁老李:(敲脑袋)呸,死豆芽懂什么啊,那都是为你好!等你以后就知道班主任的好了。我不仅在教你编程知识,还在教你怎样正确编程。

蒋 豆 芽:(捂脑袋)好,老李,你继续吧。

隔壁老李:豆芽,你想想你平时编写程序时,直接填充数字会遇到什么问题?

蒋 豆 芽:(恍然大悟)哦,修改的时候特别麻烦,过几天再来看,就忘了这个数字什么意思了。

隔壁老李:所以啊,如果我们在程序中直接填充数字或字符串,

(1)程序的可读性(可理解性)变差。我们总会忘记这些数字或字符串代表什么意义。

(2)一旦数字很多,改动麻烦。

为了避免这些问题,我们就要用常量来替代。豆芽,之前我已经跟你说过了,在C语言中,可以使用宏替代常量,而C++尽量使用const常量替代宏常量,豆芽你来回顾一下。

img

1.8 Const——今天必须把它搞懂

img

蒋 豆 芽:简单!const 是 constant 的缩写,本意是不变的,不易改变的意思。在 C++ 中是用来修饰内置类型变量,自定义对象,成员函数,返回值,函数参数。

C++ const 允许指定一个语义约束,编译器会强制实施这个约束,允许程序员告诉编译器某值是保持不变的。如果在编程中确实有某个值保持不变,就应该明确使用const,这样可以获得编译器的帮助。

在C++中为了安全性,我们就要少用甚至不要再用宏了,不带参数的宏命令我们可以用常量const来替代,比如const double PI = 3.1415,可以起到同样的效果,而且还比宏安全,因为这条语句会在编译阶段进行语法检查。而宏常量在预编译阶段被替换,不会进行语法检查。

蒋 豆 芽:(疑惑)那老李,C语言里也有const,为什么C语言里的常量用的是宏而不是const

隔壁老李:诶?这个问题问的非常得好啊,豆芽。看样子你有在认真听哈。

蒋 豆 芽:必须的!

隔壁老李:这是因为C语言里的const和C++里的const,两者作用机制是不一样的。这也是个比较重要的知识点,老李记得曾经被面试官这样问过,当时老李没有回答出来(羞涩)

蒋 豆 芽:嘿嘿。

隔壁老李:在C语言中,const修饰的变量依然被当做变量,那么其在内存中依然有存储它的空间。并且可以通过指针间接的改变该内存空间的值。如下面例子所示:

#include <stdio.h>  
int main(){  
    const int i = 10;  
    int *p = (int *)(&i);  
    *p = 20;  
    printf("i=%d   *p=%d   \n", i, *p);  
    return 0;  
}  

结果如下:

i=20   *p=20

这里可以清楚地看到,i的值被改变了。

蒋 豆 芽:啊?那这样就违背了我们定义const的初衷了。

隔壁老李:没错,所以这就是为什么在C语言中表示常量,使用的是宏常量而非const。宏是直接替换。

蒋 豆 芽:(好奇)那C++的const机制又是怎样的呢?

隔壁老李:在C++中,C++把const看做常量,编译器会使用常数直接替换掉上面例子中对i的引用,最后的结果是i = 10,*p = 20

#include<iostream>
using namespace std; 
int main(){  
    const int i = 10;  
    int *p = (int *)(&i);  
    *p = 20;  
    cout << "i=%d" << i << "*p=%d" << *p;  //这里编译器会直接将i替换为10
    return 0;  
} 

这里需要说明的是,其实变量i的内存空间里的数值依然已经被改变了,为20。

所以千万不要轻易对 const 变量设法赋值,这会产生意想不到的行为。

蒋 豆 芽:明白了!所以C++中的const机制类似C语言中的宏,都是替换,不过C++的const是在编译阶段替换,C语言的宏是在预编译阶段替换

隔壁老李:没错!豆芽,赶紧把小笔记记起来啊,这就是标准答案啊,面试官最喜欢问了。然后我们要把const讲透,const还有其他的用法,const可以修饰指针

隔壁老李:在定义指针的时候我们可以用const来修饰

根据const出现的位置和出现的次数分为三种

  1. 指向常量的指针

  2. 常指针

  3. 指向常量的常指针

1.指向常量的指针

指针指向一个常量对象,目的是防止使用该指针来修改指向的值。

如:

const int *a;    //a指针所指向的内存里的值不变,即(*a)不变,但a可以变
int const *a;    //同const int *a;

给出实例:

int a = 10;
int b = 20;
const int *p = &a;
//该声明的意思是p指向一个const int(这里为10),因此不能使用p来修改这个值,
//换句话来说,*p的值为const,不能被修改。
*p = 20; //错误,编译报错
p = &b; //正确,const只能防止修改p指向的值,但不能防止修改p的值,也就是说,可以将一个新地址赋给p

2.常指针

将指针本身声明为常量,这样可以防止改变指针指向的位置。

如:

int *const a;    //a指针所指向的内存地址不变,即a不变,但(*a)可以变

给出实例:

int a = 10;
int b = 20;
int *const p = &a;
//意思是p只能指向a,p不能变,但允许p来修改a的值。
*p = 20; //正确,a的值可以被修改
p = &b; //错误,编译报错,p不能被修改

3.指向常量的常指针

一个常量指针指向一个常量对象

如:

const int *const a;   //都不变,即(*a)不变,a也不变

隔壁老李const可以修饰参数传递

对于 const 修饰函数参数可以分为三种情况。

A:值传递的 const 修饰传递,一般这种情况不需要 const 修饰,因为函数会自动产生临时变量复制实参值,实参反正不会变。但是我们也可以加const,这是一种良好的风格。

#include<iostream> 
using namespace std;
void douya(const int a){
    cout<<a;
    // ++a;  是错误的,a 不能被改变
}

int main(void) {
    douya(8);
    system("pause");
    return 0;
}

B:当 const 参数为指针时,可以防止指针被意外篡改。

#include<iostream> 
using namespace std; 
void douya(int *const a){ 

剩余60%内容,订阅专栏后可继续查看/也可单篇购买

<p> - 本专刊适合于C/C++已经入门的学生或人士,有一定的编程基础。 - 本专刊适合于互联网C++软件开发、嵌入式软件求职的学生或人士。 - 本专刊囊括了C语言、C++、操作系统、计算机网络、嵌入式、算法与数据结构等一系列知识点的讲解,并且最后总结出了高频面试考点(附有答案)共近400道,知识点讲解全面。不仅如此,教程还讲解了简历制作、笔试面试准备、面试技巧等内容。 </p> <p> <br /> </p>

全部评论
声明类内静态变量,是需要定义的。这里要注意
点赞
送花
回复
分享
发布于 2021-07-26 10:03
请问下第一天看,第二天就忘了咋办,每天还要做实验🤧
点赞
送花
回复
分享
发布于 2023-03-22 21:20 甘肃
秋招专场
校招火热招聘中
官网直投

相关推荐

点赞 1 评论
分享
牛客网
牛客企业服务