一、KISS
1、概念
這個是目測最簡單的原則了,KISS原則:Keep It Simple And Stupid(Short、Straightforward)。不管是小括號裏的哪種解釋,最終表達的含義都是儘量保持簡單。代碼足夠簡單,也就意味着很容易讀懂,bug 比較難隱藏。即便出現 bug,修復起來也比較簡單。
2、怎麼纔算“簡單”
完成同一個需求所用的代碼行數越少就越簡單了嗎?我覺得未必!我覺得簡單二字應該是代碼行數越少而且易讀纔算簡單。舉個最傻X的例子,你TM用二進制給我寫一堆代碼完成一個需求,假設這個需求你這個代碼行數很少,但是誰看的懂?這簡單嗎…?看下面的例子,三段代碼,每段都是實現ip校驗規則的。
// 第一種實現方式: 使用正則表達式
public boolean isValidIpAddressV1(String ipAddress) {
if (StringUtils.isBlank(ipAddress)) return false;
String regex = "^(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|[1-9])\\."
+ "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\."
+ "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)\\."
+ "(1\\d{2}|2[0-4]\\d|25[0-5]|[1-9]\\d|\\d)$";
return ipAddress.matches(regex);
}
// 第二種實現方式: 使用現成的工具類
public boolean isValidIpAddressV2(String ipAddress) {
if (StringUtils.isBlank(ipAddress)) return false;
String[] ipUnits = StringUtils.split(ipAddress, '.');
if (ipUnits.length != 4) {
return false;
}
for (int i = 0; i < 4; ++i) {
int ipUnitIntValue;
try {
ipUnitIntValue = Integer.parseInt(ipUnits[i]);
} catch (NumberFormatException e) {
return false;
}
if (ipUnitIntValue < 0 || ipUnitIntValue > 255) {
return false;
}
if (i == 0 && ipUnitIntValue == 0) {
return false;
}
}
return true;
}
// 第三種實現方式: 不使用任何工具類
public boolean isValidIpAddressV3(String ipAddress) {
char[] ipChars = ipAddress.toCharArray();
int length = ipChars.length;
int ipUnitIntValue = -1;
boolean isFirstUnit = true;
int unitsCount = 0;
for (int i = 0; i < length; ++i) {
char c = ipChars[i];
if (c == '.') {
if (ipUnitIntValue < 0 || ipUnitIntValue > 255) return false;
if (isFirstUnit && ipUnitIntValue == 0) return false;
if (isFirstUnit) isFirstUnit = false;
ipUnitIntValue = -1;
unitsCount++;
continue;
}
if (c < '0' || c > '9') {
return false;
}
if (ipUnitIntValue == -1) ipUnitIntValue = 0;
ipUnitIntValue = ipUnitIntValue * 10 + (c - '0');
}
if (ipUnitIntValue < 0 || ipUnitIntValue > 255) return false;
if (unitsCount != 3) return false;
return true;
}
哪種最符合KISS原則?也就是哪種最簡單?第一種顯然代碼行數最少,但是不易讀。第三種性能肯定最高,但是是自己寫的容易出問題,我覺得如果ip校驗沒影響到性能的話,那麼這麼做就是過度優化。第二種就很完美,採取靠譜的庫來完成需求,代碼量也不大且易讀。這就叫KISS原則。也並非複雜邏輯就不符合KISS了,比如一些算法,KMP、動態規劃、樹等,這些本身就很複雜,所以我覺得沒必要談KISS。
3、如何寫出滿足KISS原則的代碼
- 儘量別用同事可能看不懂的東西寫代碼(並不是說高端技術,而是比如正則、一長串的三目表達式等)
- 別重複造輪子,善於使用已經有的工具類庫
- 別過度優化
二、YAGNI
YNGNI:You Ain’t Gonna Need It. 也就是說你不會需要它。其實也是再說不要過度設計。舉個最傻X的例子:我這項目Mysql就夠了目前不用Redis,那就別把Redis的代碼都寫了,沒必要這種過度的設計。你不需要它。
再比如:我們依賴的jar包,比如maven的gav座標,你不需要xxx.jar,就別把它的gav寫進來,這種的做法其實也是違背YAGNI原則的。
三、總結
KISS說的是如何做的簡單的問題,YAGNI說的是要不要做的問題,還是有區別的。