每月IT摘录201812

技术

1.JVM、Java并发、NIO、网络通信,这些都是一个java工程师必须具备底层技术素养。
2.关于技术广度。消息中间件、分布式缓存、海量数据、分布式搜索、NoSQL、分布式架构、高并发、高可用、高性能,这些技术,并不是说真的要求工作几年的同学每个技术都精通到源码层面,而是说你工作几年以后,应该有一定的技术广度,开阔的技术视野。各种技术你都得适当的了解一些,同时尽可能有机会的话在自己负责的项目里多实践各种技术,多体会各种技术如何组成出一套架构来解决公司的技术难题的,尽量多对各种技术都一定的实践经验。
3.技术深度的考察是中大型互联网公司面试官对一个高级/资深以上的候选人必须考察的,因为如果一个人工作5年以上,来应聘高级职位的话,那我们绝对是要求他对至少一个技术领域有着较为深入的研究的,比如说起码你得深入阅读过某个热门技术的核心源码,有一定的技术功底,可以解决一些复杂的线上故障。因为技术广度决定了你可以利用各种技术来做项目,但是技术深度决定了你的技术功底,你未来学新东西有多快,线上系统出了故障你能否快速定位和解决,你能否基于对技术的深刻理解为公司的项目设计和开发出复杂而且优秀的架构出来。
4.现在一些中大型互联网公司的面试官,很多都是技术水平非常不错的兄弟。在面试候选人的时候,一般都会采取连环炮的策略来深挖一个候选人的技术水平。
说说你们公司线上生产环境用的是什么消息中间件?
那你们线上系统是有哪些技术挑战,为什么必须要在系统里引入消息中间件?
你们的消息中间件技术选型为什么是Kafka?为什么不用RocketMQ或者是RabbitMQ?技术选型的依据是什么?
你们用的是Kafka?那你说说Kafka的底层架构原理,磁盘上数据如何存储的,整体分布式架构是如何实现的,如何保证数据的高容错性,零拷贝等技术是如何运用的,高吞吐量下如何优化生产者和消费者的性能?那你看过Kafka的源码没有,说说你对Kafka源码的理解?
如果让你来动手实现一个分布式消息中间件,整体架构你会如何设计实现?
5.红黑树,是一种二叉查找树。节点标记为红色或黑色,根节点必须是黑色,规律是“有红必有黑,红红不相连”
6.强迫自己在代码开发前,多画一些架构图、数据流程图,写代码的时候也强迫自己代码分层,经过半年的磨炼,渐渐的也能写出一些松耦合高内聚的代码,也改变了满屏if-else乱飞的现象。
7.容器技术:docker是容器。 Kubernetes(k8s)是Google开源的容器集群管理系统
8.FutureTask 是一个支持取消的异步处理器,一般在线程池中用于异步接受callable返回值。
主要实现分三部分:
封装 Callable,然后放到线程池中去异步执行->run。
获取结果-> get。
取消任务-> cancel。
9.OSGi(Open Service Gateway Initiative)技术是Java动态化模块化系统的一系列规范。
10.应用层的知识都是次要的,学到的编程能力和编程思维才是最重要的,毕竟一门通,门门通。况且对于程序员来说,编程能力和编程思维占了 80%,其他 api 的运用只占了 20%
11.Rpc和RestFul的比较:
RPC的思想是把本地函数映射到API,也就是说一个API对应的是一个function,我本地有一个getAllUsers,远程也能通过某种约定的协议来调用这个getAllUsers。至于这个协议是Socket、是HTTP还是别的什么并不重要; RPC中的主体都是动作,是个动词,表示我要做什么。
而REST则不然,它的URL主体是资源,是个名词。而且也仅支持HTTP协议,规定了使用HTTP Method表达本次要做的动作,类型一般也不超过那四五种。这些动作表达了对资源仅有的几种转化方式。
12.技术必须和业务情景结合,才能更好地地理解。
13.无论是RocketMQ、Kafka还是RabbitMQ,都有类似的autoAck或者是手动ack的机制。线上生产环境中运行时,你必须要考虑到消费者服务可能宕机的问题。如果消费者服务没处理完消息就自己宕机了,那么一定会导致部分消息的丢失,进而影响核心业务流程的运转。
14.秒杀一般用redis。如果不想用nosql,非要用数据库,就得加一个version字段。(除了设置version解决,也可以用使用状态表示来解决)
(1)首先是程序读取select version, left from table;
(2)然后记录version字段(旧值),判定left - buyCount(购买数量)>=0,如果否退出,结束业务。否则继续(3)
(3)开始执行减库存
update table set left = left - #{byCount} , version = version+1
where count >0 and vesion = #{vesion}//这个version是旧值,而更新一次成功version就加1
这里数据库并没有任何锁,但是这里巧妙的使用了version字段,符合一个CAS原理,就是我当初读出的version(旧值)和实时数据库的version(当前需要更新时刻的实时值)是否一致,如果一致,则我会认为这条记录没有被其他线程修改,则减库存成功,如果不一致则我会认为其他线程修改过这个记录。就不会进行操作这个被称为乐观锁。这个时候我们会考虑重入,重复执行(1)-(3)步骤直至(2)的退出或者(3)成功继续我们的操作,这样就是一个没有锁的机制。这就是一个乐观锁的机制,而没有任何等待的机制,是一个非阻塞的过程。
最好使用redis去完成秒杀的话。redis提供的事务很好的符合了秒杀的功能。
首先任何线程执行redis的操作的时候都是使用lua语言,redis在执行lua语言的时候是原子性的,让它执行减库存,并且记录用户购买记录。
直至秒杀时间到期或者库存为0,才考虑将redis缓存的数据批量一次性把减库存和用户购买的信息批量写入mysql。整个秒杀过程基本在redis完成,而不是数据库,不是mysql的性能可比的,服务器上mysql一秒可以4万次,redis可以上百万次
15.在zookeeper中,leader主要负责读写,follower 负责同步,只负责备份。
16.ACK (Acknowledgement)即是确认字符,在数据通信中,接收站发给发送站的一种传输类控制字符。 表示发来的数据已确认接收无误。 在TCP/IP协议中,如果接收方成功的接收到数据,那么会回复一个ACK数据。在消息队列中也存在ACK机制。
17.并发中的常用操作:
(1) 如果一个对象的成员变量有一个线程对它进行写操作,即set赋值。多个线程对它进行读操作,即get取值。就用volatile轻量级锁关键字修饰。
(2) 如果是多写多读,就请在get set方法加synchronize关键字加锁,或者用并发包下的Lock包下的显示锁加锁。
(3) 加锁有个缺点,每次getset都让你的线程多一步获取锁的操作。如果你不想对这个成员变量的读写方法加锁又要保证线程安全就请用Atomic包下的原子变量定义这个成员变量,它是用CAS无锁算法实现的。ConcurruntHashMap就用了它。
(4)如果你既想定义成员变量又不希望它共享给多个线程从而带来并发问题,你就用ThreadLocal定义这个成员变量,它是每个线程独立使用,各自不可见的。

学习

1.坚持刻意学习。不断反馈纠错。自我测试。主动学习。跳出舒适区。多复习加强记忆。
2.项目驱动的学习方法:学习一段时间,做个小项目,将做项目遇到的问题记下来,针对性地学习相关知识,然后再实践,再学一段时间理论,让知识成网状发射状地变大。当然,项目驱动式学习有一个弊端,就是每次学习的知识都是项目所需要的,很零碎、不成体系,所以需要改良,即在采取项目驱动学习法的时候每天抽一段时间去完整地读一本书,或者一个相关问题的完整介绍,这样就很容易把一些知识成体系地串起来。这样一段时间下来,慢慢的,你就知道我们为什么要学那么多科目,学这些科目能干什么。
3.有些人最爱问的一句话就是,你学成这样学了多长时间?大家好像都在暗中较劲儿,他花了多少天学完了什么什么,我就应该比他更快,因为没几个人愿意承认自己比别人笨。我觉得这种比较是毫无意义的,因为每个人的基础、时间、资源、天赋、环境都不一样,每个人学到的深度也不一样,怎么比?越比越焦躁
4.如果你想做好一件事,那就每天去做。包括圣诞节,复活节和审判日。没有例外。
5.实施细节并不是知识,而是操作步骤。如果技术栈发生变更,实施细节就会毫无用处。但是,你又不能不学习它,不知道实施细节,就没法做出项目。我觉得,程序员应该要警惕,不要落入实施细节的陷阱,不要把全部精力花在实施细节上面,然后以为自己学到了真正的知识。对待各种语言和工具,正确的态度应该是“进得去,出得来”,既要了解足够的细节,也要能够站在宏观的角度看待它,探寻底层到底是怎么实现的。

工作

1.公司要抛弃你时,可能你上午还在干活,下午就得滚蛋了。只有不断地提高竞争力,才不会被淘汰。
2.关于项目经验。介绍产品时面试官会考察应聘者的沟通能力和思考能力,我们大部分情况都是做产品的一个功能或一个模块,但是即使是这样,自己有没有把整个系统架构或产品弄清楚,并能介绍清楚,为什么做这个系统?这个系统的价值是什么?这个系统有哪些功能?优缺点有哪些?如果让你重新设计这个系统你会如何设计?
3.跳出舒适圈,找到目标是前进的起点。如果你在自己当下的工作中无法接触太多的新技术,可以尝试多去外面公司面试,这能在一定程度上帮助自己找到学习的目标;
跳槽要趁早,杜绝成为温水里的青蛙。对于想跳槽到大公司的同学来说,一定要趁早。因为同样的水平情况下,大公司更会看中「潜力」—— 年龄越大,潜力越小;
始终保持你的学习欲。对于工程师来说,学习永无止境。但埋头苦学是不够的,你要注意自己的学习一定要有系统性,除了手头的项目和身边“大牛”的指导外,看书和网络课程是最有效的方法,用少量的金钱换取宝贵的时间,是非常值得的。
如果你依然觉得有些茫然,不如跟有多年Java开发经验的资深工程师聊一聊。
4.如果你是个写Java的,我不仅想知道你会不会写Java,我还想知道你是怎么写的,在什么样的平台上?运用了哪些框架?相关配套技术有哪些?数据库有哪些?到底写了个什么东西?为谁写的?是给公司内部使用还是做甲方的项目?是负责架构设计还是模块开发还是后期的bug调试?除了Java还会别的么?我对你了解地越多,我就越能判断出你是不是适合应聘的职位,这对我们后期的沟通就越有效。
5.你做过什么样的项目?给哪家公司做的?多大的体量?最终使用人群是多少?
你在项目中的角色是什么?是参与者还是组织者还是负责人?是负责前期客户需求沟通还是后期项目交付?达到了什么样的结果?客户对你的评价是什么?有提前完成项目的经历么?
这个项目给你带来的经验是什么?是否能够积累一定的行业资源?这只是我们从一个项目中就能分析出来的信息。
而多个项目组合起来来看,我们就能清晰地感知到候选人的主要客户主要base在哪些行业或是领域?都是什么样级别的客户?而他对话的人在甲方又是什么样level的?
6.将简历名称命名为“应聘职位-姓名-毕业学校-现处公司-工作年限”
7.简历项目经验:“我参与了手机XX网发布系统WAPCMS的开发(这部分是大家都会写的)。作为核心程序员,我不但完成了网站界面、调度队列的开发工作,更提出了高效的组件级缓存系统,通过碎片化缓冲有效的提升了系统的渲染效率。(这部分是很多同学忘掉的,要写出你在这个项目中具体负责的部分,以及你贡献出来的价值。)在该系统上线后,Web前端性能从10QPS提升到200QPS,服务器由10台减少到3台(通过量化的数字来增强可信度)。2008年我升任WAPCMS项目负责人,带领一个3人小组支持着每天超过2亿的PV(这就是Benefit。你能带给前雇主的价值,也就是你能带给新雇主的价值。)”
有同学问,如果我在项目里边没有那么显赫的成绩可以说怎么办?讲不出成绩时,就讲你的成长。因为学习能力也是每家公司都看中的东西。你可以写你在这个项目里边遇到了一个什么样的问题,别人怎么解决的,你怎么解决的,你的方案好在什么地方,最终这个方案的效果如何。
具体、量化、有说服力,是技术简历特别需要注重的地方。
8.简历项目经验:我在此项目负责了哪些工作,分别在哪些地方做得出色/和别人不一样/成长快,这个项目中,我最困难的问题是什么,我采取了什么措施,最后结果如何。这个项目中,我最自豪的技术细节是什么,为什么,实施前和实施后的数据对比如何,同事和领导对此的反应如何。

生活

1.“用出世的精神做入世的事业”--朱光潜。

其他

  1. 几千年来一切都在改变,但唯有人性没有变。把握了人性,了解了人性的欲望和弱点,掌握了人性的贪婪、嫉妒、骄傲、好逸恶劳,你就掌握了打开人心的钥匙,你就掌握了智慧。
原文地址:https://www.cnblogs.com/expiator/p/10126730.html