程序员的基本功--怎样阅读代码
从学习Java第一天开始,从第一次写代码运行hello World!!程序,进入到Java程序员的大门。我也有很多的感触,看到博客里面很多大佬,都写一些自己学习的经验,我也是非常的向往。虽然我还是一个渣渣,第一次写的不好,希望大家能够体谅。
相信刚学习Java的同学们,都会遇到一个小问题。我们大家都会到网上搜一些前辈们写好的优秀代码,然后自己在本地研究,用来提升自己的水平。想当初我也是这样的,网上典型的代码一搜一大把,但是明明每个单词我都认识,但是组合在一起就不知道它是在表达啥。只知道他是一个方法,运行之后出来一个结果,方法内部如何运转,看了两三句就被绕的晕头转向。
解决这个问题就有很多的办法,网上很多大佬也都有说明,不过个人感觉不太适合自己,还是看不懂别人写的代码。今天第一次写博客我就分享自己读写代码的一个小技巧。
代码的读写,对于每一个立志的程序员都是基础中的基础,因为我们到公司上班的时候,不可能一过来就要开始写代码。我们的第一件事,就是读懂别人写好的代码,只有读懂了以前的代码,才嫩最大可能避免bug。
在eclipse中的项目目录下面,有每一个项目的文件夹。文件夹里面,是每一个我们写好的类,借口,以及配置文件。今天我想说的就是如何读懂一个类,不过里面写的多么复杂,我们都能在最短的 时间里面搞清楚他的逻辑关系。
例子我从简单到复杂一一列举,希望大家能够看得更加明白
// 程序的入口 public static void hello(){ // 向控制台输出信息 System.out.println(“hello world"); }
我们大家熟悉的入门代码,hello world。
先分析一个方法的结构。修饰符 返回值 方法名 (参数){ 方法体 }
修饰符:这个没有难度,相信大家都懂
返回值:可以为空,也可以为对象,字符串,数组 ,集合 情况复杂
方法名:规范的代码尽量做到见名知意
参数:可以为基本数据类型,对象,类 ,借口 ,可变参 情况复杂
方法体:方法功能的逻辑实现
通过分析可以发现:我们要想快速读懂一个方法,就要研究一下参数和返回值。
有人就会问了,方法中的方法体不是最重要的部分吗,为啥要先研究参数和返回值呢??
我来打个比方,一个方法就像一个小工厂,参数就是原料,返回值就是成品。看到原料和成品,我们就大致知道,这个方法使用实现什么的。
比如上面的例子,参数和返回值都为空,注定这个方法复杂不起来。
在举个例子:
1 package cn.e3mall.controller; 2 3 import java.util.HashMap; 4 import java.util.Map; 5 6 import org.springframework.beans.factory.annotation.Value; 7 import org.springframework.http.MediaType; 8 import org.springframework.stereotype.Controller; 9 import org.springframework.web.bind.annotation.RequestMapping; 10 import org.springframework.web.bind.annotation.ResponseBody; 11 import org.springframework.web.multipart.MultipartFile; 12 13 import cn.e3mall.common.utils.FastDFSClient; 14 import cn.e3mall.common.utils.JsonUtils; 15 16 /** 17 * 图片上传处理Controller 18 * <p>Title: PictureController</p> 19 * <p>Description: </p> 20 * <p>Company: www.itcast.cn</p> 21 * @version 1.0 22 */ 23 @Controller 24 public class PictureController { 25 26 @Value("${IMAGE_SERVER_URL}") 27 private String IMAGE_SERVER_URL; 28 29 @RequestMapping(value="/pic/upload", produces=MediaType.TEXT_PLAIN_VALUE+";charset=utf-8") 30 @ResponseBody 31 public String uploadFile(MultipartFile uploadFile) { 32 try { 33 //把图片上传的图片服务器 34 FastDFSClient fastDFSClient = new FastDFSClient("classpath:conf/client.conf"); 35 //取文件扩展名 36 String originalFilename = uploadFile.getOriginalFilename(); 37 String extName = originalFilename.substring(originalFilename.lastIndexOf(".") + 1); 38 //得到一个图片的地址和文件名 39 String url = fastDFSClient.uploadFile(uploadFile.getBytes(), extName); 40 //补充为完整的url 41 url = IMAGE_SERVER_URL + url; 42 //封装到map中返回 43 Map result = new HashMap<>(); 44 result.put("error", 0); 45 result.put("url", url); 46 return JsonUtils.objectToJson(result); 47 } catch (Exception e) { 48 e.printStackTrace(); 49 Map result = new HashMap<>(); 50 result.put("error", 1); 51 result.put("message", "图片上传失败"); 52 return JsonUtils.objectToJson(result); 53 } 54 } 55 }
public String uploadFile(MultipartFile uploadFile) {方法体}
我们要是第一次见到这个方法的话,你会怎么去快速理解阅读?
我会这样去理解:1、返回值 是一个字符串 对应着return JsonUtils.objectToJson(result);这句代码
2、 参数 MultipartFile uploadFile是一个MultipartFile的对象,形参名称为uploadFile
清楚了这两点之后,就要紧紧盯着参数uploadFile,可以想象自己是一个监视着,看着它怎么一步步”变成” 字符串的。也就是说方法体里面的东西都是对参数uploadFile,进行缝缝补补,最后把它制造成一个字符串.
在这个过程中,你只需要注意参数的改变,比如上面例子中,第36句往参数uploadFile中装了一个文件,然后重新换了一个新名字originalFilename,第37句对originalFilename进行substring处理一下,又换了一个名字extName;第39句将extName当成参数传入到新的方法中,生成一个结果,又重新换了一个名字.我想说的我们可以完全忽略这些来回换的新名字,不要被这些新名字晃花了眼睛.我们完全可以认为,第36,37,39这三句代码都是对参数uploadFile进行封装,直接可以不用管那些新名字有什么特殊的意思,直接忽视.当成原始参数来看待,就像一个人穿衣服,不管他穿了多少套衣服,这个人不会变对不对,我们直接忽略这些衣服,认准这个人就行了.你注意这些衣服没有任何的意义,因为衣服随时都会变,而且每个程序员给代码起名字,都不一样.就像一句老话,以不变应万变.在代码中不变是什么,对于一个方法来说,就是参数和返回值.在执行期间对参数的转化包装,我们不必深究,这个新名字会不会有什么新的含义,特殊的东西.其实根本没有必要.
第一次写,明明想要表达的意思,就是找不到合适的词语来表达.其实我想说的还是没有说的太清楚,总之一句话,以不变应万变.