http://chenyu-hz.iteye.com/blog/1005302
Java重构示例一
本文通过Java示例代码片段展示了常用重构原则和技巧,供初级开发人员参考。精致的代码能够清楚传达作者的意图,精致的代码是最好的注释,精致的代码非常容易维护和扩展。程序员阅读精致的代码如同大众欣赏优美的散文一样享受。
1 尽量简洁
1.1 重构前
if ( flag == 1 ){ return true; } else{ return false; }
|
1.2 重构后
return flag == 1;
|
2 使用三位运算符
2.1 重构前
if ( "Male".equals(gender) ) { return "Mr."; } else{ return "Mrs."; }
|
2.2 重构后
return "Male".equals(gender) ? "Mr." : "Mrs.";
|
3 使用常量替换硬编码
3.1 重构前
for (int i = 0; i < 12; i++) { this.getDays(i); //skip... }
|
3.2 重构后
int YEAR_MONTHS = 12; for (int month = 0; month < Month.YEAR_MONTHS; month++) { this.getDays(month); //skip... }
|
4 使用方法替换反复出现的表达式
4.1 重构前
public boolean isStartAfter(Date date) { Calendar calendar = BusinessCalendar.getCalendar(); calendar.setTime(date); int hour = calendar.get(Calendar.HOUR_OF_DAY); int minute = calendar.get(Calendar.MINUTE);
return ( (hour<fromHour) || ( (hour==fromHour) && (minute<=fromMinute) ) ); }
public boolean includes(Date date) { Calendar calendar = BusinessCalendar.getCalendar(); calendar.setTime(date); int hour = calendar.get(Calendar.HOUR_OF_DAY); int minute = calendar.get(Calendar.MINUTE);
return ( ( (fromHour<hour) || ( (fromHour==hour) && (fromMinute<=minute) ) ) && ( (hour<toHour) || ( (hour==toHour) && (minute<=toMinute) ) ) ); }
|
4.2 重构后
private boolean tailGreatHead(int headHour, int headMinute, int tailHour, int tailMinute, boolean includeEqual) { boolean tailGreatHeadHour = (headHour < tailHour); boolean tailEqualHeadHour = (headHour == tailHour); boolean tailGreatHeadMinute = (headMinute < tailMinute); boolean tailEqualHeadMinute = (headMinute == tailMinute);
boolean tailGreatEqualHeadMinute = tailGreatHeadMinute || includeEqual && tailEqualHeadMinute;
return (tailGreatHeadHour || (tailEqualHeadHour && tailGreatEqualHeadMinute)); }
private boolean tailGreatHead(int headHour, int headMinute, int tailHour, int tailMinute) { return tailGreatHead(headHour, headMinute, tailHour, tailMinute, false); }
private boolean tailGreatEqualHead(int headHour, int headMinute, int tailHour, int tailMinute) { return tailGreatHead(headHour, headMinute, tailHour, tailMinute, true); }
public boolean isStartAfter(Date date) { Calendar calendar = BusinessCalendar.getCalendar(); calendar.setTime(date); int hour = calendar.get(Calendar.HOUR_OF_DAY); int minute = calendar.get(Calendar.MINUTE);
return this.tailGreatEqualHead(hour, minute, fromHour, fromMinute); }
public boolean includes(Date date) { Calendar calendar = BusinessCalendar.getCalendar(); calendar.setTime(date); int hour = calendar.get(Calendar.HOUR_OF_DAY); int minute = calendar.get(Calendar.MINUTE);
return this.tailGreatEqualHead(fromHour, fromMinute, hour, minute) && this.tailGreatEqualHead(hour, minute, toHour, toMinute); }
|
5 及早结束非正常逻辑
5.1 重构前
int count = 0; if(taskList != null && !taskList.isEmpty()){
//skip...
return count; } else { return count; }
|
5.2 重构后
int count = 0; if(taskList == null || taskList.isEmpty()){ return 0; }
//skip...
return count;
|
6 满足条件立即跳出循环
6.1 重构前
public boolean contain(int year, Month month, int day) { boolean found = false; for (IPolyDate date : dateList) { if (date.same(year, month.getMonth(), day)) { found = true; break; } }
return found; }
|
6.2 重构后
public boolean contain(int year, Month month, int day) { for (IPolyDate date : dateList) { if (date.same(year, month.getMonth(), day)) { return true; } }
return false; }
|
7 使用表结构分离公共逻辑,避免重复(坚持DRY原则)
7.1 重构前
public void testGetIntPart() throws Exception { assertEquals("0", digitTransform.getIntPart("0.01"); assertEquals("1", digitTransform.getIntPart("1.2"); assertEquals("1234", digitTransform.getIntPart("1234"); assertEquals("1", digitTransform.getIntPart("1.01"); assertEquals("0", digitTransform.getIntPart("0.01"); assertEquals("11111", digitTransform.getIntPart("11111"); assertEquals("1000", digitTransform.getIntPart("1000.11"); }
|
7.2 重构后
public void testGetIntPart() throws Exception { String[][] cases = new String[][] { { "0.01", "0" }, { "1.2", "1" }, { "1234", "1234" }, { "1.01", "1" }, { "0", "0" }, { "11111", "11111" }, { "1000.11", "1000" } };
for (int i = 0, len = cases.length; i < len; i++) { assertEquals(cases[i][1], digitTransform.getIntPart(cases[i][0])); } }
|
8 分离变化参数,使用格式化方法
8.1 重构前
public class ExceedMaxWeekIndexOfMonthException extends IndexOutOfBoundsException {
private static final long serialVersionUID = 1L;
public ExceedMaxWeekIndexOfMonthException(String message) { super(message); }
}
|
8.2 重构后
public class ExceedMaxWeekIndexOfMonthException extends IndexOutOfBoundsException {
private static final long serialVersionUID = 1L;
public ExceedMaxWeekIndexOfMonthException(int index, int maxCountOfWeekDay, Month month) { super(formatMessage(index, maxCountOfWeekDay, month)); }
private static String formatMessage(int index, int maxCountOfWeekDay, Month month) { return "Arguement index[" + index + "] exceeds max week index[" + maxCountOfWeekDay + "] of month[" + month.toString() + "]."; }
}
|
9 使用方法抽取公共逻辑
9.1 重构前
public int getYear() { Calendar date = this.getCalendarDate();
return date.get(Calendar.YEAR); }
public int getMonth() { Calendar date = this.getCalendarDate();
return date.get(Calendar.MONTH); }
public int getDay() { Calendar date = this.getCalendarDate();
return date.get(Calendar.DAY_OF_MONTH); }
public int getHour() { Calendar date = this.getCalendarDate();
return date.get(Calendar.HOUR_OF_DAY); }
public int getMinute() { Calendar date = this.getCalendarDate();
return date.get(Calendar.MINUTE); }
public int getSecond() { Calendar date = this.getCalendarDate();
return date.get(Calendar.SECOND); }
public int getMillisSecond() { Calendar date = this.getCalendarDate();
return date.get(Calendar.MILLISECOND); }
|
9.2 重构后
private int get(int field) { Calendar date = this.getCalendarDate();
return date.get(field); }
public int getYear() { return this.get(Calendar.YEAR); }
public int getMonth() { return this.get(Calendar.MONTH); }
public int getDay() { return this.get(Calendar.DAY_OF_MONTH); }
public int getHour() { return this.get(Calendar.HOUR_OF_DAY); }
public int getMinute() { return this.get(Calendar.MINUTE); }
public int getSecond() { return this.get(Calendar.SECOND); }
public int getMillisSecond() { return this.get(Calendar.MILLISECOND); }
|
10 尽量使用已有的Java API
10.1 重构前
protected String[] getConfigLocations() { String[] baseCfgs = this.getBaseCfgs(); String[] extra = this.getExtraCfgs(); if (extra != null && extra.length > 0) { int baseCfgLen = baseCfgs.length; int extraLen = extra.length; String[] cfgLocations = new String[baseCfgLen + extraLen]; for(int i = 0; i < baseCfgLen; i++){ cfgLocations[i] = baseCfgs[i]; }
for(int i = 0; i < extraLen; i++){ cfgLocations[baseCfgLen + i] = extra[i]; }
return cfgLocations; } else { return baseCfgs; } } |
10.2 重构后
protected String[] getConfigLocations() { String[] baseCfgs = this.getBaseCfgs(); String[] extra = this.getExtraCfgs(); if (extra != null && extra.length > 0) { int baseCfgLen = baseCfgs.length; int extraLen = extra.length; String[] cfgLocations = new String[baseCfgLen + extraLen; System.arraycopy(baseCfgs, 0, cfgLocations, 0, baseCfgLen); System.arraycopy(extra, 0, cfgLocations, baseCfgLen, extraLen;
return cfgLocations; } else { return baseCfgs; } }
|
11 使方法通用化
11.1 重构前
public DayPart[] sortDayPart() { if (dayParts == null || dayParts.length == 0) { return dayParts; } List<DayPart> dayPartList = Arrays.asList(dayParts);
|