嵌入式C语言面试相关知识------关键字
一、博客声明
又是一年一度的秋招,怎么能只刷笔试题目呢,面试题目也得看,想当好厂的牛马其实也不容易呀O(∩_∩)O。注意:这篇博客大部分是来自网上的资源,我只是为了加深印象,总结和抄一遍,没错,就是抄一遍,相关链接放在下面。
借鉴内容链接:C语言关键字,不为人知的细节解读
二、C语言关键字
1、sizeof关键字
sizeof
在面试中会经常结合strlen()
一起问它们之间的区别,虽然它们都是与计算内存大小有关,但是他们的作用是不相同的。两者的区别在于:
sizeof
是一个运算符;而strlen()
是一个函数。sizeof
计算的是变量或类型所占用的内存字节大小;而strlen()
计算的是字符串中字符的个数,或者说是字符数组中元素的个数。sizeof
的语法是sizeof(data type)
,即sizeof
可以用于计算任何类型的数据;而strlen()
的语法是strlen(const char* str)
,即只能用于计算字符串或者字符数组。sizeof
如果计算字符串的长度,会把末尾的字符串结束符\0
也计算上;strlen()
计算时,不会包含末尾的字符结束符\0
。也就是说,用它们去计算字符串Hello
的长度,前者的结果是6 ,而后者的结果是5。
2、static关键字
面试中会被经常问这个关键字的作用,如下:
- 在修饰局部变量时,
static
修饰的静态局部变量有且只执行一次初始化任务,所以静态局部变量每次被幅值都会保存 。而且延长了局部变量的生命周期,直到程序运行解释后才会被释放。即静态局部变量所在的.c文件运行结束才会被释放,而普通的局部变量在它所在的函数调用结束后就被释放了。还有一点是,普通局部变量被存放在RAM中的 栈(Stack) 区域,被static
修饰的静态局部变量被采访在 数据段(data) 区域。 - 在修饰全局变量时,这个全局变量只能在本文件中访问,也就是限定了其作用域,不能在其他文件中进行访问,即便是使用
extern
外部声明也不可行。 - 在修饰函数时,也是会被限定其作用域,被修饰的函数只能在本文件中调用,不能被其他文件调用。
static
修饰的变量采访在全局数据区的静态变量区,包括全局静态变量和局部静态变量,均在全局数据区分配内存。初始化的时候自动初始化为0。
tips:extern
与static
不能同时使用;因为用static修饰的全局变量被限定了作用域,所以其他文件中可以有同名的全局变量被定义声明。
3、const关键字
该关键字在面试中经常被问其作用,也会被问到与#define
的区别。
- 作用: 用于定义只读变量,即如果一个变量被
const
修饰,那么它的值将无法再被更改。值得注意的是,const
定义的是变量,而不是常量。在C99标准中,const
定义的变量是全局变量,存放在全局数据区。此外,用const
修饰变量时,一定要给变量初始化幅值,否者编译器会报错。 - 与#define的区别:
1、const
常量有数据类型,而宏定义常量没有数据类型,只是简单的文本替换。因此,前者会有类型检查,而后者没有;
2、const
常量有作用域,只在它定义的作用域中有效,而宏定义常量没有作用域,可以在文件的任何地方使用。
4、volatile关键字
该关键字经常被问到作用和理解。
了解这个关键字之前,我们需要了解一下编译器的一个优化操作。由于内存访问的数据远不及CPU处理速度,为了提高存取速度,编译器优化时会把内存变量缓冲到寄存器中,若变量由其他程序所改变,其内存中的值会发生改变,而寄存器中的值不会改变, 将出现不一样的现象。volatile
单词的意思就是易变的,当修饰变量时,就会告诉编译器,这个变量容易因为其他原因被发生改变,因此编译器每次读取的时候都从原始地址中进读取。作用如下:
- 告诉编译器不要缓冲变量: 当你将一个变量声明为
volatile
时,编译器会知道这个变量可能在任何时候被外部因素(如硬件、中断服务程序、线程等)改变,因此被volatile
修饰后,编译器不会对这个变量执行优化操作。 - 确保每次访问都是直接从内存中进行读取: 每次读取
volatile
时,编译器都会生成代码从内存中读取该变量的值,而不是使用之前储存在寄存器或者其他地方的值。 - 在多线程和硬件交互特别有用: 在多线程环境中,一个线程可能正在修改一个变量,而另外一个线程正在读取该变量。如果不使用
volatile
进行修饰,编译器可能会优化读取操作,导致读取到的是旧值。同样,当与硬件交互时,硬件可能会在任何时候改变某个内存位置中的值,因此也需要使用volatile
来确保读取到的是最新的值。
5、extern关键字
该关键字经常被用到作用。
- 当在多个源文件中共享全局变量时,通常在一个源文件中定义该变量(即分配储存空间),而在其他源文件中使用
extern
声明该变量,以便能够访问它。