经典面试题目C语言
题一,堆和栈的区别是?
题二,Volatile与Register的区别是?
题三,ARM里的大端格式和小端格式分别是什么意思?
题一答案:
(1)存储内容不同
栈:在函数调用时,栈中存放的是函数中(最底下是函数调用后的下一条指令)的各个参数(局部变量)。
堆:一般是在堆的头部用一个字节存放堆的大小。堆中的具体内容由程序员分配。
(2)管理方式上不同
栈:由系统自动分配并释放空间。 例如,声明在函数中一个局部变量 int b; 系统自动在栈中为b开辟空间,当对应的生存周期结束后栈空间被自动释放。
堆:需要程序员指定大小手动申请和手动释放,在C语言中使用malloc函数申请,使用free函数释放。
(3)空间大小不同
栈:获取空间较小。在Windows下一般大小是1M或2M,当剩余栈空间不足时,分配失败overflow。
堆:获得空间根据系统的有效虚拟内存有关,比较灵活、大。
(4)能否产生碎片不同
栈:不会产生碎片,空间连续。
堆:采用的是链表的存储方式,会产生碎片。
(5)生长方向不同
栈: 向低地址扩展的数据结构,是一块连续的内存区域。
堆: 向高地址扩展的数据结构,是不连续的内存区域。这是由于系统是用链表空闲内存地址来存储的,自然不连续,而链表的遍历方向是由低地址向高地址。
(6)分配方式不同
栈:有2种分配方式:静态分配和动态分配,静态由编译器完成,例如局部变量;动态由malloc函数实现,由编译器进行释放。
堆: 都是动态分配的,没有静态分配的堆。
(7)分配效率不同
栈:由系统自动分配,速度较快。但程序员无法控制。
堆:由new分配的内存,一般速度比较慢,而且容易产生内存碎片,不过用起来最方便。
题二答案:
a.volatile
volatile是易变的,不稳定的意思,volatile是关键字,是一种类型修饰符,用它修饰的变量表示可以被某些编译器未知的因素更改,比如操作系统、硬件或者其他线程等,遇到这个关键字声明的变量,编译器对访问该变量的代码不在进行优化,从而可以提供对特殊地址的稳定访问。那么什么是编译器优化呢?
为了提高运行效率,攻城师们费尽心机地把代码优化,优化程序运行时存取速度。一般,分为硬件优化和软件优化。硬件优化,流水线工作,详细可以参考《计算机组成原理》。软件优化,一部分是程序猿们做的代码优化(前提你得有优化的思路和能力),还有一部分就是我们的编译器优化了。
现代的编译器经过那么多年的发展,已经比较成熟,它会把多余的变量忽略掉,让代码的运行效率更高。默认情况下,编译器都会对代码进行优化,会把一些变量在寄存器里存取,而不是在内存里存取,如此一来,CPU在自己家里拿东西当然比从内存那里拿东西要快得多。举个小栗子:
int i = 5;
int a = i;
……
int b = i;
编译器发现两次从i读数据的代码之间,并没有对i进行过操作,它会自动把上次读的数据放在b中,而不是重新从i里面读取。
而volatile关键字告诉编译器该变量是随时可能发生变化的,每次使用它的时候必须从内存中取出它的值,因而编译器生成的汇编代码会从原内存地址中读取数据使用,而不是从寄存器或者缓存中读取,从而保证了对特殊地址的稳定访问。
简言之,状态要经常变化的,为了防止我们编译优化而导致的存取的数据不同步的问题,这时我们就需要用到volatile。那具体到什么场景下需要用到volatile关键字呢?
1、并行设备的硬件寄存器(如:状态寄存器);
2、一个中断服务子程序中会访问到的非自动变量();
3、多线程应用中被几个任务共享的变量;
上面提到了非自动变量,这里进一步对几种变量做一番解释:
自动变量:是在函数内部定义和使用的变量,它是局部变量。
非自动变量:有两种,一种是全局变量,一种是静态变量。
全局变量:在函数外面定义的变量,只能定义一次,不能有重复的定义,不然就会发生错误,而其他的文件要想使用这个变量,需要extern来声明这个变量(也可省略,因为默认就是extern),这个声明叫做引用声明。
若不想被其他文件访问,则用static关键字声明为静态变量。静态变量与自动变量的本质区别是,静态变量并不像自动变量那样使用堆栈机制来使用内存。
而是为静态变量分配固定的内存,在程序运行的整个过程中,它都会被保持,而不会被销毁。这就是说静态变量的持续性是程序运行的整个周期。这有利于我们共享一些数据。
如果静态变量在函数内部定义,则它的作用域就是在这个函数内部,仅在这个函数内部使用它才有效,但是它不同于自动变量,自动变量离开函数后就会被销毁,而静态变量不会被销毁。他在函数的整个运行周期内都会存在。
b. register
这个关键字请求编译器尽可能的将变量存在CPU内部寄存器中,而不是通过内存寻址访问,以提高效率。注意是尽可能,不是绝对。你想想,一个CPU 的寄存器也就那么几个或几十个,你要是定义了很多很多register 变量,它累死也可能不能全部把这些变量放入寄存器吧。
题三答案:
当前的存储器,多以byte为访问的最小单元,当一个逻辑上的地址必须分割为物理上的若干单元时就存在了先放谁后放谁的问题, 于是端(endian)的问题应运而生了, 对于不同的存储方法, 就有大端(big-endian)和小端(little- endian)两个描述。
字节排序按分为大端和小端,概念如下
大端(big endian): 低地址存放高有效字节
小端(little endian): 低字节存放低有效字节
现在主流的CPU, intel系列的是采用的little endian的格式存放数据,而motorola系列的CPU采用的是big endian,ARM则同时支持 big和little。
举个例子
int a = 0x12345678;
a是四字节的int类型变量,需要占四个字节空间,假设变量a的首地址是0x2000,那么数据存储在地址中的格式如下:
---------end-------
题一,同步和异步有啥区别?
题二,TCP与UDP有啥区别?
题三,进程和线程有啥区别?
题一答案:
同步(Sync):所有的操作都做完,才返回给用户。这样用户在线等待的时间太长,给用户一种卡死了的感觉(比如系统迁移中,点击了迁移,界面就不动了,但是程序还在执行,卡死了的感觉)。
这种情况下,用户不能关闭界面,如果关闭,那么迁移程序也会中断,用户体验不好。
异步(Async):将用户请求放入消息队列,并反馈给用户,比如系统迁移程序已经启动,提示你可以关闭浏览器了。然后程序再慢慢地写入数据库。但是用户没有卡死的感觉,用户体验较好。
题二答案:
1、TCP面向连接(如打电话要先拨号建立连接);UDP是无连接的,即发送数据之前不需要建立连接
2、TCP提供可靠的服务。它通过校验和,丢包时的重传控制,序号标识,滑动窗口、确认应答,次序乱掉的分包进行顺序控制实现可靠传输。即通过TCP连接传送的数据,无差错,不丢失,不重复,且按序到达; UDP尽最大努力交付,即不保证可靠交付。
3、UDP具有较好的实时性,工作效率比TCP高,适用于对高速传输和实时性有较高要求的通信或广播通信场景。
4、每一条TCP连接只能是点到点的; UDP支持一对一,一对多,多对一和多对多的交互通信方式。
5、TCP对系统资源要求较多,UDP对系统资源要求较少。
UDP有时比TCP更有优势:
UDP以其简单、传输快的优势,在越来越多场景下取代了TCP, 如实时游戏。
(1)网速的提升给UDP的稳定性提供可靠网络保障,丢包率很低,如果使用应用层重传,能够确保传输的可靠性。
(2)TCP为了实现网络通信的可靠性,使用了复杂的拥塞控制算法,建立了繁琐的握手过程,由于TCP在内置的系统协议栈中,极难对其进行改进。
采用TCP,一旦发生丢包,TCP会将后续的包缓存起来,等前面的包重传并接收到后再继续发送,延时会越来越大。
基于UDP对实时性要求较为严格的情况下,采用自定义重传机制,能够把丢包产生的延迟降到最低,尽量减少网络问题造成的影响。
题三答案:
1. 进程是资源分配的最小单位。
2. 线程是程序执行的最小单位,也是处理器调度的基本单位,但进程不是,两者均可并发执行。
3. 进程有自己的独立地址空间,每启动一个进程,系统就会为它分配地址空间,建立数据表来维护代码段、堆栈段和数据段,这种操作非常昂贵。而线程是共享进程中的数据,使用相同的地址空间,因此,CPU切换一个线程的花费远比进程小很多,同时创建一个线程的开销也比进程小很多。
4. 线程之间的通信更方便,同一进程下的线程共享全局变量、静态变量等数据,而进程之间的通信需要以通信的方式(IPC)进行。不过如何处理好同步与互斥是编写多线程程序的难点。但是多进程程序更健壮,多线程程序只要有一个线程死掉,整个进程也跟着死掉了,而一个进程死掉并不会对另外一个进程造成影响,因为进程有自己独立的地址空间。
5. 进程切换时,消耗的资源大,效率高。所以涉及到频繁的切换时,使用线程要好于进程。同样如果要求同时进行并且又要共享某些变量的并发操作,只能用线程不能用进程。
6. 执行过程:每个独立的进程有一个程序运行的入口、顺序执行序列和程序入口。但是线程不能独立执行,必须依存在应用程序中,由应用程序提供多个线程执行控制。
优缺点:
线程执行开销小,但是不利于资源的管理和保护。线程适合在SMP机器(双CPU系统)上运行。
进程执行开销大,但是能够很好的进行资源管理和保护,可以跨机器迁移。
何时使用多进程,何时使用多线程?
对资源的管理和保护要求高,不限制开销和效率时,使用多进程。
要求效率高,频繁切换时,资源的保护管理要求不是很高时,使用多线程。
<wiz_tmp_tag id="wiz-table-range-border" contenteditable="false" style="display: none;">
经典面试题目C语言的更多相关文章
- 33条C#、.Net经典面试题目及答案
33条C#..Net经典面试题目及答案[zt] 本文集中了多条常见的C#..Net经典面试题目例如".NET中类和结构的区别"."ASP.NET页面之间传递值的几种方式? ...
- 33条C#、.Net经典面试题目及答案[zt]
33条C#..Net经典面试题目及答案[zt] 本文集中了多条常见的C#..Net经典面试题目例如“.NET中类和结构的区别”.“ASP.NET页面之间传递值的几种方式?”,并简明扼要的给出了答案,希 ...
- 经典面试题目——250M内存处理10G大小的log文件
前言 周末逛知乎的时候,看到的一个经典面试题目:http://www.zhihu.com/question/26435483.非常经典的一道分而治之的题目. 题目描写叙述例如以下: 有次面试遇到一个问 ...
- C语言经典面试题目(转的,不过写的的确好!)
第一部分:基本概念及其它问答题 1.关键字static的作用是什么? 这个简单的问题很少有人能回答完全.在C语言中,关键字static有三个明显的作用: 1). 在函数体,一个被声明为静态的变量在这一 ...
- cc++面试------17道经典面试题目分析
以下是C/C++面试题目,共计17个题目,其中涵盖了c的各种基础语法和算法, 以函数接口设计和算法设计为主.这17个题目在C/C++面试方面已经流行了多 年,大家需要抽时间掌握好,每一个题目后面附有参 ...
- 2017最新PHP经典面试题目汇总(上篇)
1.双引号和单引号的区别 双引号解释变量,单引号不解释变量 双引号里插入单引号,其中单引号里如果有变量的话,变量解释 双引号的变量名后面必须要有一个非数字.字母.下划线的特殊字符,或者用{}讲变量括起 ...
- PHP经典面试题目汇总(上篇)
1.双引号和单引号的区别 双引号解释变量,单引号不解释变量 双引号里插入单引号,其中单引号里如果有变量的话,变量解释 双引号的变量名后面必须要有一个非数字.字母.下划线的特殊字符,或者用{}讲变量括起 ...
- PHP经典面试题目汇总
1.双引号和单引号的区别 双引号解释变量,单引号不解释变量 双引号里插入单引号,其中单引号里如果有变量的话,变量解释 双引号的变量名后面必须要有一个非数字.字母.下划线的特殊字符,或者用{}讲变量括起 ...
- 33条C#和.NET经典面试题目及答案
1. .NET中类和结构的区别? 答:结构和类具有大体的语法,但是结构受到的限制比类要多. a. 结构不能有默认的构造函数,因为结构的副本是用编译器创建和销毁的,所以不需要默认的构造函数和析构函数. ...
随机推荐
- pstree命令详解
基础命令学习目录首页 pstree命令是用于查看进程树之间的关系,即哪个进程是父进程,哪个是子进程,可以清楚的看出来是谁创建了谁#pstree几个重要的参数:-A: 各进程树之间的连接以ASCII码字 ...
- Spring的bean创建详解
IoC容器,又名控制反转,全称为Inverse of Control,其是Spring最为核心的一个组件,其他的组件如AOP,Spring事务等都是直接或间接的依赖于IoC容器的.本文主 ...
- “Hello World!”Final发布文案加美工
文案: 大家好,我们是“Hello World!”团队,本次我将向大家简要介绍一下空天猎的final发布,在空天猎final发布中,我主要从以下两个方面向大家进行介绍,第一个方面是增加了敌方的boss ...
- final发布视频展示博客
Part One [探路者]选题展示视频链接: http://v.youku.com/v_show/id_XMzIxMDM2MTQ1Ng==.html?spm=a2h3j.8428770.341605 ...
- 文件上传到tomcat服务器 commons-fileupload的详细介绍与使用
三个类:DiskFileUpload.FileItem和FileUploadException.这三个类全部位于org.apache.commons.fileupload包中. 首先需要说明一下for ...
- 假如 GFW 遇上 ML
我稍微试了一下梯子 我稍微试了一下梯子,在有梯子的情况下进行google搜索,然后wireshark 抓包.所有问题跃然纸上 当前我认为:> 只要你和一个非国内的服务器长时高频交换数据,基本上就 ...
- 深入理解JAVA集合系列一:HashMap源码解读
初认HashMap 基于哈希表(即散列表)的Map接口的实现,此实现提供所有可选的映射操作,并允许使用null值和null键. HashMap继承于AbstractMap,实现了Map.Cloneab ...
- 转 彻底理解js中的&&和||
javascript中,&&和||的用法比较神奇,经常用在对象上,例如a || b,如果a不存在,则返回b.a && b,如果a存在,则返回b,否则返回a. 光这样看, ...
- LeetCode题解:(139) Word Break
题目说明 Given a non-empty string s and a dictionary wordDict containing a list of non-empty words, dete ...
- Sql Server自增ID与序号的使用
SQL 自增ID alter table a add id int identity(1,1) not null 这里为 a 表增加一个 id 字段,其中identity(1,1)代表自增,第一个1代 ...