变量初始化
重构手法
变量初始化最好一次完成
能用final的地方建议都用final,包括变量声明,参数声明,类声明,方法声明
案例1
1 2 3 4 5 6 7
| EpubStatus status = null; CreateEpubResponse response = createEpub(request); if (response.getCode() == 201) { status = EpubStatus.CREATED; } else { status = EpubStatus.TO_CREATE; }
|
- 问题:第一行的初始化没有意义,他真正有值是在第4行或者第6行。也就是说声明变量后很久才赋值。变量初始化和业务混在了一起,我们只有在一大堆逻辑中抽丝剥茧,才可以知道变量是如何初始化的。
- 修正:
1 2 3 4 5 6 7 8 9 10
| final CreateEpubResponse response = createEpub(request); final EpubStatus status = toEpubStatus(response);
private EpubStatus toEpubStatus(final CreateEpubResponse response) { if (response.getCode() == 201) { return EpubStatus.CREATED; } return EpubStatus.TO_CREATE; }
|
案例2(异常处理)
1 2 3 4 5 6 7 8 9 10 11 12
| InputStream is = null;
try { is = new FileInputStream(...); ... } catch (IOException e) { ... } finally { if (is != null) { is.close(); } }
|
这里把is单独声明,是为了在finally里面可以访问到,在早期的版本只能写成这样,java7之后的版本,可以采用try-with-resource
的写法,代码更加简洁。
修正:
1 2 3
| try (InputStream is = new FileInputStream(...)) { ... }
|
案例3 集合初始化
1 2 3 4 5 6 7 8 9
| private static Map<Locale, String> CODE_MAPPING = new HashMap<>(); ...
static { CODE_MAPPING.put(LOCALE.ENGLISH, "EN"); CODE_MAPPING.put(LOCALE.CHINESE, "CH"); }
|
问题: 隔了很久后才向这个集合中添加元素,如果我们可以使用一次性声明的方式,这个static块是不需要的
修正:
1 2 3 4
| private static Map<Locale, String> CODE_MAPPING = ImmutableMap.of( LOCALE.ENGLISH, "EN", LOCALE.CHINESE, "CH" );
|
前者是命令式的代码,告诉你“怎么做”,比如先创建一个集合,集合中添加一个元素,再添加一个元素。
后者是声明式代码,告诉你“做什么”,比如我要一个包含了这两个元素的集合。