腾讯视频社招算法题记录:不使用锁的情况下用N个线程循环打印到数字M

111 阅读4分钟

背景

非常非常难得有了一次梦中情厂腾讯的面试机会,虽然官网没有对应岗位的信息,面试也是略显粗糙地直接通过短信/邮件+腾小T小程序进行安排和通知的,但是还是抱着一定期待进行。整体下来面试1个小时多10来分钟这样,感觉答的还行的,原以为会有下一轮的机会没想到当晚没两个小时腾小T查询状态就进人才库了,感觉还是挺郁闷失落的,花了点时间消化了一下情绪。别的东西可能略带一些多角度的理解不太好复盘,还是针对一下算法题记录一下

算法题

本身面试来的很紧,周一发的面试信息,腾小T给了周二下午,周二晚上和周三下午三个时间让选择,为了有一定复习时间选择了周三,仅有一天多的时间自己其实复习就没特别刷题了,还是针对项目和八股整体过了一遍,预设了一些问题想了想回答思路,顺便查漏补缺了一下。面试过程中也是面试官相对详尽地把项目过了一下,又单拎了一些八股问题问,整体还感觉正中下怀,大概四五十分钟下来,感觉也快一小时了,也不会出算法了吧,没想到还是从腾讯会议的窗口撸了一个小程序地窗口让写一下,心里还是一慌的毕竟没有刷题

题目:不使用锁的情况下用N个线程循环打印到数字M。

面试官出完题补充说,实在想不到也可以加锁写

听完第一感觉就是肯定不能加锁写,加锁写就是一个给你体面的机会,就算写出来也要挂,先前试过的所有面试,写算法阶段给一个转圜余地的做法的,我就是写出来也都给挂了,当时的想法就是硬着头皮也得不加锁写

思路: 首先还是,n个线程就得用循环来创建对应数目的线程

其次打印需要有一个共享的数据来作为循环的对象,并作为打印的对象持续维护递增。

然后题目不使用锁的话,乐观锁的思路直接就想到需要用一个循环一直跑,通过条件控制进入来实现数据递增。不加锁的话第一时间就很容易考虑要保证数据的可见性,这个循环的维护才成立,所以维护的数据要加volatile关键字。

然后由于n个线程按顺序打印,那么很好看出每个线程打印的数字都会有取余得到的值相同的关系,根据这个关系来令这个打印的顺序得以保证。

自己用Android Studio写了一下

b03046a9b93686fe44cbf4f18f03301.png

跑面试题的用例:

267f3e7949baa1239e0b39e33a24f48.png

面试的时候因为写题前问了ThreadLocal是什么的八股问题,看到给的用例也想着这题目里每个线程是不是也需要区分,又用了一个ThreadLocal去存一个数字,但是自己复盘写的时候好像这玩意儿也没用上,只保证这个取余关系就已经够用了。实际面试官看完也说这里是不是有点多余,实在要也可以声明一个类继承然后用一个成员变量就好。。

意外收获与反思总结

写的时候想不起来题目用例给的是4,8还是4,7来着,心血来潮打开腾讯会议想着进入历史会议会不会有,也没抱太大希望。没想到还真能进去,进去还能找到当时出题内容,甚至还要自己当时写的情况,截了个图

25cb2ca82589535097feaaea7ef197c.png

只能说想是一回事,实际写也是一回事。虽然当时写完直接表示没有办法run一下调试不一定是一段ac的代码,所以口述了思路,然后面试官听完说循环和判断条件可能还有问题,但是思路可以大致是可行的,给了一些肯定的说辞。但是根据这个实际当时写的情况来说,估计run也确实没法跑出来,只能说现在的竞争形势,只能自己面试的时候还是得尽力做到ac吧