当前位置:   article > 正文

2020九家大厂面试题及答案集锦,面试胸有成竹,入职水到渠成!_宇凡星面试题

宇凡星面试题

给大家整理了腾讯、阿里、百度、华为、头条等一共九家大厂2020年的面试题以及答案,篇幅所限,我就每家的只放两道题了,有需要完整版的朋友可以评论区留言或进群973961276获取。缺乏项目实战经验的小老弟可以点这里☞c/c++企业级项目实战

文末还给大家放了一份学习大纲,如果看完文章能顺手给我点个赞那就再好不过了。

一、腾讯

1.删除字符串s1中在字符串s2中出现的字符。

基本思路:把s1的字符存到一个set里面,然后遍历s2,看是否出现过,出现过就erase掉。但是直接输出set的元素这样会改变顺序,要想顺序不变,就顺序遍历一下s1 看是否出现,出现就输出。

  1. #include <iostream>
  2. #include <cstdio>
  3. #include <cstring>
  4. #include <cmath>
  5. #include <algorithm>
  6. #include <vector>
  7. #include <set>
  8. #include <queue>
  9. #include <map>
  10. using namespace std;
  11. typedef long long LL;
  12. const int maxn=1005;
  13. set<char>s;
  14. int main()
  15. {
  16. string s1,s2;
  17. cin>>s1>>s2;
  18. int len=s1.length();
  19. for (int i=0;i<len;i++)
  20. s.insert(s1[i]);
  21. len=s2.length();
  22. for (int i=0;i<len;i++)
  23. {
  24. if (s.count(s2[i]))
  25. s.erase(s.find(s2[i]));
  26. }
  27. len=s1.length();
  28. for (int i=0;i<len;i++)
  29. {
  30. if (s.count(s1[i]))
  31. cout<<s1[i];
  32. }
  33. cout<<endl;
  34. return 0;

2. 求一个论坛的在线人数,假设有一个论坛,其注册ID有两亿个,每个ID从登陆到退出会向一个日志文件中记下登陆时间和退出时间,要求写一个算法统计一天中论坛的用户在线分布,取样粒度为秒。

答案:

一天总共有3600*24=86400秒。

定义一个长度为86400的整数数组intdelta[86400],每个整数对应这一秒的人数变化值,可能为正也可能为负。开始时将数组元素都初始化为0。

然后依次读入每个用户的登录时间和退出时间,将与登录时间对应的整数值加1,将与退出时间对应的整数值减1。

这样处理一遍后数组中存储了每秒中的人数变化情况。

定义另外一个长度为86400的整数数组intonline_num[86400],每个整数对应这一秒的论坛在线人数。

假设一天开始时论坛在线人数为0,则第1秒的人数online_num[0]=delta[0]。第n+1秒的人数online_num[n]=online_num[n-1]+delta[n]。

这样我们就获得了一天中任意时间的在线人数。

二、阿里巴巴

1、使用mysql索引都有哪些原则?索引什么数据结构? B+tree和B tree什么区别?

答案:

1、    对于查询频率高的字段创建索引;

2、    对排序、分组、联合查询频率高的字段创建索引;

3、    索引的数目不宜太多 原因:a、每创建一个索引都会占用相应的物理控件; b、过多的索引会导致insert, update、delete语句的执行效率降低;

4、    若在实际中,需要将多个列设置索引时,可以采用多列索引 如:某个表(假设表名为Student),存在多个字段(StudentNo, StudentName, Sex, Address, Phone, BirthDate),其中需要71 StudentNo, StudentName 字段进行查询,对 Sex字段进行分组,对BirthDate字段逹行排序,此时可以创建多列索引index index_najne (StudentNo, StudentName, Sex, BirthDate) ;#index_najne 为索引名 在上面的语句中只创建了一个索引,但是对4个字段都赋予了豪引的功能。 创建多列索引,需要遵循BTree类型,即第一列使用时,才启用索引。 在上面的创建语句中,只有mysql语句在使用到StudentNo字段时,索引才会被启 用。 如: select * from Student wheie StudentNo = 1000; #使用到了 StudentNo 字段,索引被启用。 以使用explain检测索引是否被启用如:explain select * from Student where StudentNo = 1000;

5、    选择唯一性索引 唯一性索引的值是唯一的,可以更快速的通过该索引来确定某条记录。例如,学生 表中学号是具有唯一性的字段。为该字段建立唯一性索引可以很快的确定某个学生的 信息。如果使用姓名的话,可能存    在同名现象,从而降低查询速度。

6、    尽量使用数据量少的索引 如果索引的值很长,那么查询的速度会受到影响。例如,对一个CHAR (100)类型的 字段进行全文检索    需要的时间肯定要比对CHAR (10)类型的字段 需要的时间要多。

7、    尽量使用前缀来索引 如果索引字段的值很长,最好使用催的前缀来索引。例如,TEXT和BLOG类型的字 段,进行全文检索会很浪费时间。如果只检索字段的前面的若干个字符,这样可以提 高检索速度。

8、    删除不再使用或者很少使用的索引. 表中的数据被大量更新,或者数据的使用方式被改变后,原有的一些索引可能不再 需要。数据库管理员应当定期找出这些索引,将它们删除,从而减少索引对更新操作 的影响B+ tree树索引,B tree,散列

2、Mysql有哪些存储引擎?请详细列举其区别?

答案:

InnoDB:事务型存储引擎,并且有较高的并发读取频率

MEMORY:存储引擎,存放在内存中,数据量小,速度快

Merge: ARCHIVE:归档,有很好的压缩机制

3、设计高并发系统数据库层面该如何设计?数据库锁有哪 些类型?如何实现?

答案:

分库分表:同样量的数据平均存储在不同数据库相同表(或不同表)中,减轻单表 压力,如果还是很大,就可以每个库在分多张表,根据hash取值或者其他逻辑判断将 数据存储在哪张表中

读写分离:数据库原本就有主从数据库之分,查询在从服务器,増删改在主服务器,

归档和操作表区分:建一张归档表,将历史数据放入,需要操作的表数据单独存储

索引之类的创建,对于数据量很大,百万级别以上的单表,如果増删改操作不频 繁的话,可以创建bitMap索引,速度要快得多

       共享锁:要等第一个人操作完,释放锁,才能操作

       更新锁:解决死锁,别人可以读,但不能操作

       排他锁:读写都被禁用

       意向锁(xlock):对表中部分数据加锁,查询时,可以跳过

       计划锁:操作时,别的表连接不了这张表

三、百度

1、输入www.baidu.com在浏览器的完整过程,越详细越好。

答案:

浏览器获取输入的域名ww. baidu. com

浏览器向域名系统

DNS请求解析ww. baidu. com的IP地址 DNS解析出百度服务器的IP地址

浏览器与服务器建立TCP连接(默认端口 80)

浏览器发出HTTP请求,请求百度首页

服务器通过HTTP请求把首页文件发给浏览器

TCP连接释放

浏览器解析首页文件,展示web界面

2、请描述C/C++程序的内存分区?

答案:

其实c和c卄的内存分区还是有一定区别的,但此处不作区分:

1)    、栈区(stack)-由编译器自动分配軽放,存放函数的参数值,局部变量的值等。 其 操作方式类似于数据结构中的栈。

2)    、堆区(heap) ——般由程序员分配释放,若程序员不軽放,程序结束时可能由 OS回 收。注意它与数据结构中的堆是两回事,分配方式倒是类似于链表。

3)    、全局区(静态区)(static) —,全局变量和静态变量的存储是放在一块的,初 始化的 全局变量和静态变量在一块区域,未初始化的全局变量和未初始化的静态变量在相邻 的另 —块区域。-程序结束后由系统释放。

4)    、文字常量区一常量字符串就是放在这里的。程序结束后由系统释放。

5)    、程序代码区一存放函数体的二进制代码。 栈区与堆区的区别:

    1)    堆和栈中的存储内容:栈存局部变量•,函数参数等。堆存储使用new、malloc申请 的变量等;

    2)    申请方式:栈内存由系统分配,堆内有由自己申请;

    3)    申请后系统的响应:栈一一只要栈的剩余空间大于所申请空间,系统将为程序提供 内存,否则将报异常提示栈溢出。 堆一一首先应该知道操作系统有一个记录空闲内存地址的链表,当系统收到程序的申请 时,会遍历该链表,寻找第一个空间大于所申请空间的堆结点,然后将该结点从空闲结 点链表中删除,并将该结点的空间分配蜘程序; 申请大小的限制:WindowsT栈的大小一般是2M,堆的容量较大; 申请效率的比较:栈由系统自动分配,速度较快。堆使用new、malloc等分配,较 慢;

总结:

栈区优势在处理效率,堆区优势在于灵活;

内存模型:自由区、静态区、动态区;

根据c/c++对象生命周期不同,c/c++的内存模型有三种不同的内存区域,即:自由存 储区,动态区、静态区。 自由存储区:

局部非静态变量的存储区域,即平常所说的栈; 动态区:用new , malloc分配的内存,即平常所说的堆;

靜态区:全局变量,静态变量,字符串常量存在的位置; 注:代码虽然占内存,但不属于c/c卄内存模型的一部分;

四、华为

1、static有什么用途?(请至少说明两种)

答案:

1)    在函数体,一个被声明为静态的变量在这一函数被调用过程中維持其值 不变。

2)    在模块内(但在函数体外),一个被声明为静态的变量可以被模块内所 用函数访问,但不能被模块外其它函数访问。它是一个本地的全局变量。

3)    在模块内,一个被声明为静态的函数只可被这一模块内的其它函数调用。 那就是,这个函数被限制在声明它的模块的本地范围内使用

2、引用与指针有什么区别?

答案:

1)    引用必须被初始化,指针不必。

2)    引用初始化以后不能被改变,指针可以改变所指的对象。

3)    不存在指向空值的引用,但是存在指向空值的指针。

3、某32位系统下,C++程序,请计算sizeof的值.

  1. char str[] = rthttp: //www. ibegroi5>. com/w
  2. char *p = str ;
  3. int n = 10;
  4. sizeof (str ) = ? (1)
  5. sizeof ( p ) = ? (2)
  6. sizeof ( n ) = ? (3) void Foo ( char str [100]) (
  7. mm
  8. sizeof( str ) = ?(4)
  9. }
  10. void *p = malloc( 100 );
  11. mm
  12. sizeof ( p ) = ? (5)
  13. 17 (2) 4 (3) 4 (4) 4 (5) 4

五、京东

1、求此N的最小公倍数。把每个数字分解质因数,算他们 每个质因数的贡献,然后乘起来。

  1. #include<bits/stdc++. h>
  2. using namespace std;
  3. typedef long long 11;
  4. #define maxn 100009
  5. int fact [maxn];
  6. bool prime [maxn];
  7. 11 mod = 987654321;
  8. int cal (int t, int p) {
  9. int ent = 0;
  10. while(t % p == 0) { cnt++;
  11. t /= P;
  12. return ent;
  13. void first () {
  14. memset (prime, true, sizeof (prime)); prime[1] = false;
  15. for(int i = 2; i <= 100000; i++: { int top = sqrt(i);
  16. for(int j = 2; j <= top; j—) { if(i % j == 0){ prime[i] = false; break;
  17. void solve(int Limit) { first ();
  18. for (int i = 2; i <= Limit; i++' { int top = sqrt(i);
  19. for (int j = 2; j <= top; ji) { if(prime[j] && i % j == 0) {
  20. fact[j] = max (fact [j], cal (i, j));
  21. I
  22. if(prime[i])
  23. fact [i] = max (fact [i], 1);
  24. }
  25. }
  26. int main() {
  27. 11 n;
  28. cin^^n;
  29. solve (n);
  30. 11 ans = 1;
  31. for(11 i = 1; i <= n; i++) {
  32. for (11 j = 1; j <= fact[i]; j++) {
  33. ans = ans * i % mod;
  34. }
  35. }
  36. cout<<ai^s<<endl;
  37. return 0;

2、去掉字符串构成回文。其实是经典的求回文子序列个数。

  1. # inc lude <b i t s /s t dc++. h>
  2. using namespace std;
  3. typedef long long 11;
  4. 11 f[59] [59];
  5. string str;
  6. 11 dfs(int i, int j) {
  7. i£(i > j) {
  8. return 0;
  9. }
  10. if(i == j) {
  11. f[i] [j] = 1;
  12. return f [i] [j];
  13. }
  14. [j] != 0){
  15. return f [i] [j];f [i] [j] = dfs (i, j - 1) + dfs(i + 1, j) - dfs(i + 1, j - 1); if (str [i] == str[j])
  16. f [i] [j] += dfs(i + 1, j - 1+ 1;
  17. return f [i] [j];
  18. int main。{
  19. cin>>sh;
  20. int len = str.length();
  21. cout«dfs(0, len - l)«endl;
  22. return 0;

六、美团

1、已知一个函数rand7()能够生成1-7的随机数,请给岀一个 函数,该函数能够生成1-10的随机数。

  1. 该解法基于一种叫做拒绝采样的方法。主要思想是只要产生一个目标范围内的随机数, 则直接返回。如果产生的随机数不在目标范围内,则丢弃该值,重新取样。由于目标范 围内的数字被选中的概率相等,这样一个均匀的分布生成了。
  2. 显然rand7至少需要执行2次,否则产生不了 1T0的数字。通过运行:rand7两次,可 以生成1-49的整数,
  3. 2 3 4 5 6 7
  4. 1 2 3 4 5 6 7
  5. 8 9 10 1 2 3 4
  6. 5 6 7 8 9 10 1
  7. 2 3 4 5 6 7 8
  8. 9 10 1 2 3 4 5
  9. 6 7 8 9 10 * *
  10. *******
  11. 由于49不是10的倍数,所以我们需要丢弃一些值,我们想要的数字范围为1-40,不 在此范围则丢弃并重新取样。
  12. 代码:
  13. int randlOO {
  14. int row, col, idx;
  15. do {
  16. row = randT ();
  17. col = randT ();
  18. idx = col + (row-1) *7;
  19. } while (idx > 40);
  20. return 1 + (idx-l)%10;
  21. }
  22. 由于row范围为1-7, col.范围为1-7,这样idx值范围为1-49。大于40的值被丢弃, 这样剩下1-40范围内的数字,通过取模返回。下面计算一下得到一个满足1-40范围的 数需要进行取样的次数的期望值:E(# calls to rand7) = 2 * (40/49) +
  23. 4 * (9/49) » (40/49) +
  24. 6 * (9/49)2 * (40/49) +
  25. 8
  26. =$ 2k * (9/49)k_1 » (40/49) k=l
  27. =(80/49) / (1 - 9/49)2
  28. =2.45

2、C++11创建线程的三种方式

  1. 通过暨!
  2. thread:标准库的类
  3. join:阻塞主线程并等待
  4. // MultiThread, cpp : Defines the en~ry point for the console application.
  5. #include 〃stdafx・h〃
  6. #include^iostream>
  7. #include<vec t or >
  8. #include<map>
  9. #include<string>
  10. it inc lude < thr e ad>
  11. using namespace std;
  12. void myPrint()
  13. [
  14. cout « "线程幵始运行”« endl;
  15. cout « 〃线程运行结束了” « end*std:: thread my20bj (myPrint); // 可调用对象 my20bj. joint);//主线程阻塞在这.,并等待myPrint()执行完 cout « ^wangtao^ « endl;
  16. return 0;
  17. detachO:将主线程和子线程完全分离,子线程会驻留在后台运行,被CH运行时库接 管,失去控制
  18. joinable ():判断是否可以成功使用join。或者detach()
  19. 程序说明:detach后不能在实施join std: : thread my20bj (myPrint); //主线程阻塞在这,并等待myPrint ()执行完 if (my20bj. joinable ()) {
  20. cout « ^1: joinable () == hue" « endl;
  21. }
  22. else {
  23. cout « ^1:joinable() == false” « endl;
  24. }
  25. my20bj. detachO ;
  26. if (my20bj. j oinable()) {
  27. cout « "2: joinable () == hue" « endl;
  28. }
  29. else {
  30. cout « °2:joinable() == false” « endl;
  31. I
  32. cout
  33. «
  34. 〃祁angtaol”
  35. «
  36. endl;
  37. cout
  38. «
  39. 〃祁angtao2"
  40. «
  41. endl;
  42. cout
  43. «
  44. 〃祁angtao3”
  45. «
  46. endl;
  47. cout
  48. «
  49. 〃祁angtao4〃
  50. «
  51. endl;
  52. cout
  53. «
  54. 〃祁angtao5”
  55. «
  56. endl;
  57. cout
  58. «
  59. 〃祁angtao6〃
  60. «
  61. endl;
  62. cout
  63. «
  64. ^wangtao?^
  65. «
  66. endl;
  67. cout
  68. «
  69. 〃祁angtao8〃
  70. «
  71. endl;
  72. I
  73. return 0;
  74. int
  75. main
  76. 0
  77. std:: thread my20bj (myPrint); //主线程阻塞在这,并等待myPrint ()执行完 if (my20bj. joinable ()) {
  78. my20bj. join();
  79. cout
  80. «
  81. 〃祁angtaol”
  82. «
  83. endl;
  84. cout
  85. «
  86. 〃祁angtao2"
  87. «
  88. endl;
  89. cout
  90. «
  91. 〃祁angtao3
  92. «
  93. endl;
  94. cout
  95. <<
  96. 〃wangtao4
  97. <<
  98. endl;
  99. cout
  100. «
  101. 〃祁angtao5
  102. «
  103. endl;
  104. cout
  105. «
  106. 〃祁angtao6
  107. «
  108. endl;
  109. cout
  110. «
  111. ^wangtao?^
  112. «
  113. endl;
  114. cout
  115. «
  116. 〃祁angtao8
  117. «
  118. endl;
  119. return 0;通过类对象创建线程
  120. class CObject
  121. [
  122. public:
  123. void operator () () {
  124. cout « "线程幵始运行"« endl; cout « '线程结束运行〃 « endl;
  125. int main()
  126. [
  127. CObject obj;
  128. std:: thread my20bj (obj); //主线程阻塞在这,并等待myPrint ()执行完 if (my20bj. joinable ()) {
  129. my20bj. join();
  130. }
  131. cout « see you << endl;
  132. return 0;
  133. class CObject
  134. [
  135. int& m_obj;
  136. public:
  137. CObject(int& i) :m_obj(i) {} void operator () () { // 不带参数 cout « "线程幵始运行1” « endl; cout « "线程幵始运行2” « endl; cout « "线程幵始运行3" « endl; cout « "线程幵始运行4” « endl; cout « "线程幵始运行5” « endl;
  138. int main。
  139. [
  140. int i = 6;
  141. CObject obj (i);
  142. std:: thread my20bj (obj); //主线程阻塞在这,并等待myPrint ()执行完 if (my20bj. joinable ()) {
  143. my20bj. detachO ;cout « "sue you " « endl;
  144. return 0;
  145. 用detach ()主线程结束对象即被销毁,那么子线程的成员函数还能调用吗?
  146. 这里的的对象会被复制到子线程中,当主线程结束,复制的子线程对象并不会被销毁 只要是没有引用、指针就不会出现问题
  147. 通过复制构造函数和析构函数来燈证对象是否复制到了子线程中
  148. // MultiThread. cpp : Defines the eniry point for the console application.
  149. //
  150. #include "stdafx.h”
  151. #include<iostreajn>
  152. #include<vector>
  153. Ji include〈map >
  154. #include<string>
  155. #include<thread>
  156. using namespace std;
  157. class CObject
  158. [
  159. int& m_obj;
  160. public:
  161. CObject(int& i) :m_obj(i) {
  162. cout « "ctor” « endl;
  163. }
  164. CObject(const CObject& m) :m_obj(m.m_obj) {
  165. cout « "copy ctor" « endl.
  166. }
  167. "CObject() {
  168. cout « "dtor” « endl;
  169. I
  170. void operator () () { // 不带参数
  171. cout « "线程幵始运行1” « endl;
  172. cout « "线程幵始运行2” « endl;
  173. cout « "线程幵始运行3" « endl;
  174. cout « "线程幵始运行4” « endl;
  175. cout « "线程幵始运行5” « endl;
  176. int main。
  177. [
  178. int i = 6;
  179. CObject obj (i);
  180. std:: thread my20bj (obj); //主线程阻塞在这,并等待myPrint ()执行完 if (my20bj. joinable ()) {
  181. my20bj. detachO ;
  182. }
  183. cout << see you << endl;
  184. return 0;
  185. 子线程的析构函数在后台执行,所以输出的dt皿是主线程的。用join()结果为:
  186. 通过lambda表达式创建线程
  187. int main。
  188. [
  189. auto myLamThread = [] {
  190. cout « "线程幵始运行"« endl;
  191. cout « '线程结束运行”« endl;
  192. };
  193. thread cthread(myLamThread);
  194. cthread. joint);
  195. std::cout « 〃see you " « endl.
  196. return 0;

七、头条

1、C++智能指针如何解决内存泄露问题

  1. shazedjtr共享的智能指针
  2. std::shmed_ph使用引用计数,每一个sharedjtr的拷贝都指向相同的内存。在最 后一个shared_ptr析构的时候,内存才会被释放。
  3. 可以通过构造函数、std_make_shared辅助函数和reset方法来初始化shared_ptr:
  4. //构造函数初始化
  5. std::shared_ptrp ( new int(1));
  6. std::shared_ptrp2 = p ;
  7. //对于一个未初始化的智能指针,可以通过reset方法来初始化。
  8. std::shared_ptrptr; ptr.reset ( new int (1));
  9. if (ptr) {cout « "ph is not null.\n^ ; }
  10. 不能将一个原始指针直接赋值给一个智能指针:
  11. std: : shared_ptrp = new int(l) ;//编译报错,不允许直接赋值
  12. 获取原始指针:
  13. 通过get方法来返回原始指针
  14. std::shared_ptrptr ( new int(1));
  15. int * p =ptr. get ();
  16. 指针删除器:
  17. 智能指针初始化可以指定删除器
  18. void DeletelntPtr ( int * p ) {
  19. delete p ;
  20. }
  21. std::shared_ptrp ( new int , DeletelntPtr );
  22. 当P的引用技术为o时,自动调用删除器来释放对象的内存。删除器也可以是一个 lambda表达式,例如
  23. std::shared_ptrp ( new int , [](int * p){delete p});
  24. 注意事项:
  25. .不要用一个原始指针初始化多个shared_ptro
  26. .不要再函数实参中创建Shared_ptr,在调用函数之前先定义以及初始化它。
  27. (。).不荽将lhi»指针作为 ^Cd_plx返回出来。
  28. 0).要避免循环引用。
  29. unique_ptr独占的智能指针
  30. unique_ptr是一个独占的智能指针,他不允许其他的智能指针共享其内部的指针,不 允许通过赋值将一个unique_ptr赋值给另外一个unique_ptro
  31. unique_ptr不允许复制,但可以通过函数返回给其他的unique_ptr,还可以通过 std::move来转移到其他的unique_ptr,这样它本身就不再拥有原来指针的所有权了。 如果希望只有一个智能指针管理资源或管理数组就用unique_ptr,如果希望多个智能 指针管理同一个资源就用shared_ptro
  32. weak_ptr弱引用的智能指针
  33. 弱引用的智能指针weak_ptr是用来监视sharedjtr的,不会使引用计数加一,它 不管理shared_ptr内部的指针,主要是对了监视shared_ptr的生命周期,更像是 shared_ptr的一个助手。
  34. weak_ptr没有重载运算符桥口因为它不共享指针,不能操作资源,主要是为了 通过Shared_ptr获得资源的监测权,它的构造不会増加引用计数,它的析构不会减少 引用计数,纯粹只是作为一个旁观者来监视shmed_ph中关离得资源是否存在。
  35. weak_ptr还可以用来返回this指针和解决循环引用的问题。

2、linux中软连接和硬链接的区别.

原理上,硬链接和源文件的inode节点号相同,两者互为硬链接。软连接和源文件的 inode节点号不同,进而指向的block也不同,软连接block中存放了源文件的路径名。 实际上,硬链接和源文件是同一份文件,而软连接是独立的文件,类似于快捷方式,存 備看源文件的位置信息便于指冋。 使用限制上,不能对目录创建硬链接,不能对不同文件系统创建硬链接,不能对不存在 的文件创建硬链接;可以对目录创建软连接,可以跨文件系统创建软连接,可以 对不存在的文件创建软连接。

八、中兴

1、线上CPU爆高,请问你如何找到问题所在。

答案:

1、top命令:Linux命令。可以查看实时的CPU使用情况。也可以查看最近一段时间 的CPU使用情况。

2、PS命令:Linux命令。强大的进程状态监控命令。可以查看进程以及进程中线程的 当前CPU使用情况。属于当前状态的采栏数据。

3、jstack: Java提供的命令。可以查看某个进程的当前线程栈运行情况。根据这个 命令的输出可以定位某个进程的所有线程的当前运行状态、运行代码,以及是否死锁等

4、pstack: Linux命令。可以查看某个进程的当前线程栈运行情况。

2、红黑树如何插入和删除的

答案:

插入:

(1)    如果父节点为黑色,直接插入不处理

(2)    如果父节点为红色,叔叔节点为红色,则父节点和叔叔节点变为黑色,祖先节 点变为红色,将节点操作转换为祖先节点

(3)    如果当前节点为父亲节点的右节点,则以父亲结点为中心左旋操作

(4)    如果当前节点为父亲节点的左节点,则父亲节点变为黑色,祖先节点变为红色, 以祖先节点为中心右旋操作

删除:

(1)    先按照排序二叉树的方法,删除当前节点,如果需要转移即转移到下一个节点

(2)    当前节点,必定为这样的情况:没有左子树。

(3)    删除为红色节点,不需要处理,直接按照删除二叉树节点一样

(4)    如果兄弟节点为黑色,兄弟节点的两个子节点为黑色,则将兄弟节点变为红色, 将着色转移到父亲节点

(5)    如果兄弟节点为红色,将兄弟节点设为黑色,父亲结点设为红色节点,对父亲 结点进行左旋操作

(6)    如果兄弟节点为黑色,左孩子为红色,右孩子为黑色,对兄弟节点进行右旋操 作

(7)    如果兄弟节点为黑色,右孩子为红色,则将父亲节点的颜色赋值给兄弟节点, 将父亲节点设置为黑色,将兄弟节点的右孩子设为黑色,对父亲节点进行左旋

九、滴滴

1、寻找两个有序数组的中位数

  1. double findliledianSortedArrays (vectoi<intnumsl, vector<int>& nums2) { double ret - ~1;
  2. vector<double> buff;
  3. //合并两个数组
  4. for (auto e : numsl)
  5. buff. push_back(e);
  6. for (auto a : nums2)
  7. buff. push_back(a);
  8. 合并后的结果进行排序
  9. sort (buff. beginO, buff, end:));
  10. int size3 = buff. size();
  11. /依取中位数
  12. if (size3 % 2 == 0)
  13. [
  14. ret = ((buff[size3 / 2] + buff[size3 / 2 - 1]) / 2);
  15. }
  16. else
  17. {
  18. ret = buff[size3 / 2];
  19. }
  20. return ret;
  21. }

2、c++实现线程安全的单例模式

  1. 懒汉模式:
  2. class singleton
  3. [
  4. protected:
  5. singletonO
  6. [
  7. p thr e ad_mut ex_ini t(&mutex);
  8. private
  9. static singleton* p;
  10. public
  11. static pthread__mutex_t mutex;
  12. static singleton* initance();
  13. pthread_mutex_t singleton::mutex;
  14. singleton* singleton::p = NULL;
  15. singleton* singleton::initance()
  16. [
  17. if (p == NULL)
  18. [
  19. p thr e ad_mut ex_lo ck(&mutex);
  20. if (p == NULL)
  21. p = new singletonO ;
  22. p thr e ad_mut ex_unlo ck(&mutex;;
  23. }
  24. return p;
  25. }

企业级实战项目大纲,学完轻松就业☟

我都这么有诚意了你还不关注我???

 

 

 

 

 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/黑客灵魂/article/detail/865560
推荐阅读
相关标签
  

闽ICP备14008679号