根据自己的工作经验,为哥们写的一个比较完整的j2ee的学习路径。学习周期大约6个月,目标是成为一个合格的SE。文档编写计划大概一个月内,会不断更新修正,会附上一些代码示例。
成为一个合格的SE,个人认为,知识面广而全是首要条件,基础要扎实,要了解原理和设计**。如果你只是要成为一个能编码的初级人员,这里的很多知识点对你来说可能意义不大,可能长时间用不上。比如,这里会学习servlet容器和springmvc的使用,而很多人觉得有了springboot这些都不需要学习了。但首先很多系统还是在使用springmvc,第二springboot的强包装让你忽略了太多的实现原理和细节,你只懂springboot,说实话很难应对工作中的各种情况。我的风格是知其然知其所以然,只会使用那只是初级阶段。
知识学习要一步一步来,首先是使用,然后是原理,原理好好理解之后就应该领悟**,从而融会贯通。初学者不要以为看懂了就能理解**,这种人有,但不是我。我建议扎扎实实一步一步学习,多敲代码多思考,等你的知识面广了,实现原理理解看多了,自然水到渠成。如果按照正确的道路学习6个月,技术能达到一个质的飞跃,一点都不夸张。而现实中更多的人是混混沌沌编码多年,连门都没有入。
学习过程中,最主要的是自己的实践和思考,而不只是看懂我写的东西。
开始学习的时候应该是全面铺开学习,而不是学完一个再学另外一个,如果你学玩数据结构在学线程,难度太大并且容易变成死记硬背。正确的应该学点这个再学点那个,先开始学的是应用,后面学习的是原理,代码还是那些代码,但自己的认知深度应该越来越深越来越有内涵,死记硬背也变成融会贯通就对了。这个在于自我感觉,自己心里越来越有底就对了,不会因为学到什么新的知识点而欢喜,而不会因为自己不懂什么知识点而害怕,因为你知道最重要的东西是什么,那些你学好了,其他都只是招式而已,一下子就上手了。就好比很多人花了大力气学习的springboot框架,在我这里就是很短的一章,因为我觉得他很简单,大部分是使用层面,重要的是其他知识。
另外我这个教程,不是针对一干二净的小白,针对的是有一定的学习和理解能力的人。这里不会教你怎么安装jdk,ide,也不会给你指定第一天学什么第二天学什么。我这里给的方向和重要的知识点,大家应该在方向正确的前提上自己安排自己的学习计划,重点是先广再精,不要一开始就在一个问题上钻太深,功力不到意义不大。
大纲是根据我的工作中用到的我觉得重要的点来写的。肯定不是完整的,大家批判学习吧。
重点:HashMap的数据结构、设计**和所有的细节。
- 初级
- 学习List/Map
- 如何学习
- ArrayList/LinkedList/HashMap/LinkedHashMap/TreeMap 和 Set 的使用
- hashcode的作用
- equals方法
- LinkedList是个deque,双向队列
- 使用Map实现用户crud功能
- 思考:为什么使用LinkedHashMap?
- 思考: 每一个方法输入和输出怎么样最合理?
- 思考:怎么样用最少的代码实现?
- Collections工具库使用
- 序列化的概念
- transient关键字
- 了解注解
- 学习List/Map
- 中级
- Queue/Deque
- 了解 ArrayList/LinkedList/HashMap的实现原理
- 了解 ConcurrentHashMap的实现原理
- 查看java.util包
- 反射/自省
- 自定义注解
- 泛型使用和实现原理
这块能力不能忽略,很多人懂很多知识点,却连一个复杂一点的功能都写不出来,归根到底是思维能力太差。我面试Android开发人员的时候,有1/3的人连1到100的加法递归实现都不会写。
初级里面的都是工作中用得上的知识。而中级的,说实话看着高大上,工作中基本用不上,最少我的这么多年工作中,基本没用过。
编程能力里面,最重要是函数的编写,而函数的编写里面最主要的输入参数,其次是输出参数,方法名正常人问题不会太大。当你学会了写函数,能写好函数,能把代码写短,你的编程之路会越来越轻松。
重点:练习的时候学习函数的编写。
编码习惯是开发里面最重要的一块。有些人,技术不一定很好,但写代码不会出什么错误,有问题很快能定位解决。而有些人,面试的时候知识点答得不错,但一实际工作一堆问题,每天加班加点。问题究竟出在哪里呢?
我个人觉得有2个主要原因,第1,就是编程的思维能力,第2,就是编码习惯。思维能力可以通过扩充自己的知识面、多写一些基本的代码来弥补,相对不是很难,而编码习惯这块,看着简单,实际上更加难。详细大家可以参考我的《程序员你为什么这么累?》系列贴,里面都是一些绝对的经验之谈,都是从工作中血的教训中得来的,一定要重视!!
重点:学会写漂亮的函数是工作中重中之重!比技术更加重要,让你少加班甚至不加班。编写的时候注意力放在:日志和异常处理,函数的输入输出参数,尤其是不要写重复代码(超过3行就算)。
- 函数编写
- 关注输入输出,尤其是输入
- 参数尽量使用父类/接口,越往上抽象程序越高
- 一个函数尽量只做一个事情,修改测试起来容易
- 容易变化的地方需要抽取单独方法
- 日志/异常
- 一般情况不允许捕获异常
- 对空判断需要慎重,写代码的时候应该有能不加空判断就不加的觉悟
- 需要有这样的觉悟:日志是没有人看的,除非用户找到你的时候,这个时候已经有点晚了
- 关键参数和分支需要打印日志,能从日志里面看出代码走向
- 日志初学者可以多加一点,到了后期,也应该有能不加就不加的觉悟
- 对于后台的定时任务等的异常,一定要重视,应该有通知机制,最简单就是捕获了发送邮件通知
重点:线程池、线程同步,JUC包。工作中ThreadLocal作用巨大,需要重点掌握,参考我的代码工程。
- 初级
- 线程(概念、方法和状态)
- 如何启动、停止线程
- 守护线程是什么
- 中断线程做了什么?那几个方法?
- synchronize/wait/notify关键字
- synchronize能加在什么地方?
- 线程(概念、方法和状态)
- 中级
- 线程池
- 线程通信
- ReentryLock的使用
- 重点阅读BlockingList的源码
- ThreadLocal使用
- 高级
- JUC包
- 使用synchronize/wait/notify实现BlockingList
- JVM里面和synchronize相关知识
重点:重点了解和多线程,GC相关知识点,面试必考题。
- 初级
- 引用的4中类型和OOM关系
- volatile关键字使用
- final关键字使用
- 理解java的传值
- 中级
- volatile关键字语义
- 内存屏障
- 重排序
- final关键字语义
- 避免对象逸出
- GC日志的阅读分析
- dump文件分析
- volatile关键字语义
- 高级
重点:结合http协议编写servlet代码。了解servlet 3的新特性并编码实践一遍。最起码需要用servlet返回json/试图。
- 初级
- 中级
- 实现登录功能
- springmvc框架使用
- ORM/Hibernate的使用
- 理解IOC/AOP,理解容器概念
- springboot框架使用
- 高级
- 参考我的代码框架
- 编写一个权限注解的AOP
- 用上SPEL
网页开发东西太多,难度也很大。这里不做重点讲解,只是了解基础知识。SE需要知道网页的基本工作原理。
重点: http协议字段,大部分返回码需要记住。cookie的相关关联知识需要重点掌握。
- 初级
- 了解js/css/html
- html编写原则
- jss选择器
- 使用jquery+BootStrap+模板实现功能
- http协议,重点了解post/get协议
- rest接口测试插件使用
- 了解js/css/html
- 中级
- vuejs+BootStrap+Axois实现功能
- http协议返回码
- http basic 认证
- session/cookie
- cookie的坑
- 单点登录sso实现原理
- 高级
- webpack打包
- 跨域
部署架构知识是SE的重中之重,但很多人这块认知非常薄弱。不过好消息就是这块很简单,主要是概念的理解和配置而已,没有太多动脑子的地方。但是概念很多,牵涉范围很广,需要多理解多动手,只是看懂没有太大意义。
重点:nginx的作用和配置,必须每一个特性自己配置测试一遍。知道url是在nginx还是容器处理,知道返回码是哪里返回的,对定位问题很有帮助。
- 初级
- 中级
- 使用nginx配置负载均衡
- 配置反向代理
我本人数据库水平也不好,这里给不出很好的学习建议,我只列举一下我觉得工作中的重要知识点
重点:设计一个简单论坛的数据库表全部设计。包括权限表设计,多级树表设计。
- 索引
- 索引的种类和使用场景
- 使用工具查看索引的使用情况
- 工具
- 学习DBA各种工具的使用
- 数据库表设计
- 唯一索引重要性
- 冗余数据设计的重要性
- 关系表设计
- NoSQL
- 了解种类和适用场景
- redis
设计模式很多人奉若圭臬,但我个人却没有啥感觉,工作中作用也没有那么大。个人觉得设计模式不应该孤立学习,孤立学习看着不难,但感觉容易变成死记硬背。建议是在理解实现的时候领悟设计模式,重点理解几种常用和好用的设计模式即可。
重点:重点了解常用的几种设计模式。需要联想到实际常见的场景并编码实践。只是看懂是不够的。
- 初级
- 设计模式预览
- 重点的几种设计模式
- 中级
- 重点的几种设计模式在实际中的应用
- spring的设计模式
- Class.forName / SPI / IoC
函数式编程是相对于命令式编程的另外一种**。是非常重要的一种思维、编码方式,很多语言都有,尤其前台开发里面。
重点:理解流的概念和**,map/filter/reduce方法,在js和java语言上使用一遍理解异同。不要把他当做是一个普通方法调用一下就觉得掌握了,重要的是理解**!
- 初级
- 概念理解
- 使用
- 函数式接口
- 各种方法
- 中级
- 概念深入理解
- 实现原理理解
- 高级
- jvm实现
工具使用都是初级知识,并没有难点。
重点:找几个oom的例子好好学习,自己编码重现问题并用工具分析。gc日志也要重点掌握。
- 初级
- jdk自带工具使用
- 反编译工具
- 中级
- 压力测试工具使用
- 内存分析工具使用
没啥好说的,用一次就够了。
重点:写好demo,要用的时候能想到有这个东西,并且能拿来即用。
- Guava
- Apache的common系列
- lombok
- Json库
这里重点列举一下我工作中掌握得比较好比较有用的知识,全靠比较全面的掌握这些的知识,让我在技术人员中崭露头角,编码工作非常轻松,并成为部门的疑难杂症专家。
有些技术学会后,对自己技术和思维大有帮助,但工作中却不是必不可少。如常见的数据结构的底层知识,了解得很好对面试很有帮助,但工作中不了解底层只简单了解,实际上的使用效果差距也不是很大。这些知识就成为某些只会架构不编码的“高级架构师”眼中的掉书袋。
而有些知识,你不了解的话,会走很多弯路。这些技术必须熟练掌握!
- ThreadLocal使用
- Annotation + AOP
- http协议,j2ee开发中有大一半以上问题和前台有关
- Cookie所有相关细节,这里会有非常多定位位置的时候用到的知识。
- ajax跨域
- nginx