壹 ❀ 引
當一個團隊開發同一個項目時,無論使用的是什么技術,每個人開發習慣的不同,最終代碼呈現總有差異;A同事不愛寫注釋,B同事命名上總是隨心所欲,雖然功能都能實現,但對於幾個月,或很久之后的維護造成了極大的阻礙,因此統一一個開發團隊的編程規范很有必要。這份規范幾個月前就整理好了,前端組目前的開發也以此為標准,其實對於我來說也是一種個人財富吧,所以這里還是整理為博客。
本文主要從命名、注釋、編程規范與項目文件命名四個方面展開,公司要求不同最終規范肯定不會完全一致,但願此規范能對你的提供一點思路與幫助,那么本文開始:
貳 ❀ 命名(變量/常量/函數)
1.變量
變量命名推薦采用小駝峰命名法---即首字母小寫,后每個單詞首字母大寫。
// good let name = '聽風是風'; let userName = 'echo'; // bad let username = '時間跳躍';
2.常量
常量命名推薦采用全字母大寫命名,以便於與變量區分。
// good const PI = 3.141592653; // bad const pi = 3.141592653;
3.函數
函數命名推薦使用小駝峰命名法,條件允許情況下請采用動詞前綴方式,請保證函數命名語義化明確。
// 判斷是否能執行某個操作/權限 function canLogin() {}; // 判斷是否有某個值 function hasUserName() {}; // 判斷是否是某個值 function isUserName() {}; // 獲取某個值 function getUserName() {}; // 設置某個值 function setUserName() {}; // 加載數據 function loadData() {}; // ...
4.構造函數
構造函數命名必須采用大駝峰命名法,即首字母必須大寫。
// good function Student(name) { this.name = name; };
叄 ❀ 注釋
1.單行注釋
采用 // 方式注釋:
// 這是我的博客名 let name = '聽風是風';
2.多行注釋
采用 /** */ 方式注釋:
/** * 這是我的博客名 * 聽風是風,且聽風吟 */ let name = '聽風是風';
3.函數注釋
函數注釋也是多行注釋的一種,但要求提供函數功能說明,作者信息,參數說明(若有參數),以及返回值(若有返回值)說明。
/** * @desc 用於計算兩數之和 * @author 聽風是風 * @param {Number} x 數字,用於加法計算 * @param {Number} y 數字,用於加法計算 * @return {Number} result 用於保存計算后的結果 */ function add(x, y) { let result = x + y; return result; };
肆 ❀ 編程規范
1.推薦使用對象直接量創建對象,而非構造器創建
// 創建普通對象 // good let obj = {a: 1} // bad let obj = new Object(); obj.a = 1; // 創建數組 // good let arr = [1,2,3]; // bad let arr = new Array(); arr[0] = 1; arr[1] = 2; arr[2] = 3; // 創建函數 // good function getName(){}; //函數聲明 let getName = function() {}; //函數表達式 // bad let getName = new Function();
2.字符串拼接推薦使用ES6中` `拼接
// good let str = `hello, my name is ${變量}.`; // bad let str = "hello, my name is " + 變量 + " ."
3.比較運算符
永遠推薦使用"==="與"!=="而非"=="與"!=",在允許的情況下,推薦使用比較運算符簡寫進行判斷:
// good if(a === 1){}; if(a !== 1){}
比較運算符簡寫的規則:
a.對象被認為是true
b.Undefined,Null,空字符串被計算為false
c.布爾值根據自身值判斷為true或false
d.數字+0,-0或NaN被計算為false,否則為true
// good if(name){}; // bad if(name !== ''){}; // good if(arr.length){}; // bad if(arr.length > 0){}; // good if(!variable){} // bad if(variable === false){}
4.養成添加分號的習慣
let name = '聽風是風';
const AGE = 26;
5.空格與代碼縮進
請結合vscode插件,如Beautify進行一鍵格式化。
6.代碼空行
a.函數代碼塊前后請空行(當函數方緊接函數注釋時,函數與注釋間不需要換行)
let name = '聽風是風'; //這是一個函數 function setName(name){ let userName = name; }; // 調用函數 setName(name);
b.注釋前請空行(當注釋在代碼塊的第一行時,則無需空行;若在函數內注釋可不空行,集中聲明多個變量添加注釋時也可不空行)
// 名字 let name = '聽風是風'; // 年齡 let age = 26; //這是一個函數 function setName(name){ // 設置用戶名 let userName = name; // 返回用戶名 return userName; }; // 調用函數 setName(name);
c.變量聲明下方請空行(如有多個變量集中聲明,只在最后一個變量下方空行,函數內可不空行)
7.變量、函數請保證先聲明后使用,統一作用域的變量聲明請集中管理
雖然ES6使用let已經不存在變量提升,避免了這個問題,但若仍使用了var聲明請遵守這一點。
// good var a = 1; console.log(a) // bad console.log(a) var a = 1; // good function demo() {console.log(1)}; demo(); // bad demo(); function demo() {console.log(1)};
同一作用域的變量聲明請集中在頂端。
// good function demo() { var a = 1; var b = 2; var c = 3; console.log(a); console.log(b); }; // bad function demo() { var a = 1; console.log(a); var b = 2; var c = 3; console.log(b); };
8.關於循環
a.若循環中需使用函數,請將函數定義在循環外部而非內部,這樣可以避免函數的反復創建。
// good let demo = function (i) { console.log(i) }, i = 0, arr = [1, 2, 3], len = arr.length; for (; i < len; i++) { demo(i); }; // bad let arr = [1, 2, 3], i = 0, len = arr.length; for (; i < len; i++) { let demo = function () { console.log(i); }; demo(); };
上述bad寫法中准確來說有兩點不合理,第一點是demo函數會反復創建比較浪費內存;
第二點是嚴格來說函數只能在全局作用域或函數作用域下聲明,但瀏覽器環境默認支持了非此類環境的創建行為,且ES6為了兼容早期寫法,仍然允許此類寫法,但我們應該清楚這一點。
b.循環中的常量
循環過程中例如數組的length屬性在不變的情況下,提出循環外聲明要比在for循環中創建更好。
// good let i = 0, arr = [1, 2, 3], len = arr.length; for (; i < len; i++) { console.log(i); }; // bad let arr = [1, 2, 3]; for (let i = 0; i < arr.length; i++) { console.log(i); };
c.若循環操作與循環順序無關,使用逆序遍歷效果更好
// good let arr = [1, 2, 3], len = arr.length; while (len--) { console.log(1); };
伍 ❀ 項目文件命名規范
由於我們使用了angularjs開發項目,總會涉及到組件,服務等特殊文件,這里除了常見的html,less文件外,還會統一特殊文件的命名習慣。
1.html文件命名推薦采用小駝峰命名法+.html:
index.html
myAccount.html
2.less文件推薦采用小駝峰命名法+.less:
index.less
myAccount.less
3.controller控制器推薦小駝峰命名法+Ctrl+.js:
indexCtrl.js
myAccountCtrl.js
4.service推薦采用小駝峰命名法+.service+.js:
index.service.js
myAccount.service.js
5.component推薦采用小駝峰命名法+.component+.js,依賴模板與樣式如下:
// 組件JS myAccount.component.js // 組件樣式 myAccount.component.less // 組件模板 myAccount.template.html
6.directive指令推薦小駝峰命名法+.directive+.js,模板樣式同component
// 組件JS myAccount.directive.js // 組件樣式 myAccount.directive.less // 組件模板 myAccount.template.html
7.控制器,服務,組件,指令注冊命名,推薦采用小駝峰命名
angular.module('myApp',[]) .controller('myAccountCtrl',function(){ // 控制器 }) .service('myAccountService',function(){ // 服務 }) .directive('myAccountDirective',function() { // 指令 }) .component('myAccountComponent',{ // 組件 }) .filter('myAccountFilter',function(){ // 過濾器 });
這樣統一命名的好處是,當我們看到一個服務叫myAccountService,那么馬上可以知道創建這個服務的文件名叫myAccount.Service.js。
我們保證文件名與注冊名的一致性,這樣對於文件查找是非常便捷的。
希望這些規范能對你有所幫助,本文結束。