25 编程风格
“编程风格”(programming style)指的是编写代码的样式规则。不同的程序员,往往有不同的编程风格。
25.1 缩进
2个空格
25.2区块
总是使用大括号表示区块
block{
//
}
25.3圆括号
- 表示函数调用时,函数名与左括号之间没有空格。
- 表示函数定义时,函数名与左括号之间没有空格。
- 其他情况时,前面位置的语法元素与左括号之间,都有一个空格。
// 圆括号表示函数的调用
console.log('abc');
// 圆括号表示表达式的组合
(1 + 2) * 3
foo(bar)
return (a+b);
if (a === 0) {...}
function foo(b) {...}
//匿名函数,function是语法关键字,不是函数名,所以与左括号之间应该要有一个空格。
function (x) {...}
25.4行尾的分号
分号表示一条语句的结束。JavaScript 允许省略行尾的分号。
不要省略
25.4.1 不使用分号的情况
-
for 和 while 循环
for ( ; ; ) { } // 没有分号 while (true) { } // 没有分号 //---------------------------- do { a--; } while(a > 0); // 分号不能省略
-
分支语句:if,switch,try
if (true) { } // 没有分号 switch () { } // 没有分号 try { } catch { } // 没有分号
-
函数的声明语句
function f() { } // 没有分号 //------------------- //函数表达式仍然要使用分号。 var f = function f() { };
25.4.2分号的自动添加
如果continue
、break
、return
和throw
这四个语句后面,直接跟换行符,则会自动添加分号。这意味着,如果return
语句返回的是一个对象的字面量,起首的大括号一定要写在同一行,否则得不到预期结果。
return
{ first: 'Jane' };
// 解释成
return;
{ first: 'Jane' };
不应该省略结尾的分号,还有一个原因。有些 JavaScript 代码压缩器(uglifier)不会自动添加分号,因此遇到没有分号的结尾,就会让代码保持原状,而不是压缩成一行,使得压缩无法得到最优的结果。另外,不写结尾的分号,可能会导致脚本合并出错。所以,有的代码库在第一行语句开始前,会加上一个分号。
25.5 全局变量
建议避免使用全局变量。如果不得不使用,可以考虑用大写字母表示变量名,这样更容易看出这是全局变量,比如UPPER_CASE
。
25.6变量声明
JavaScript 会自动将变量声明“提升”(hoist)到代码块(block)的头部。
if (!x) {
var x = {};
}
//变量x是if代码块之前就存在了。为了避免可能出现的问题,最好把变量声明都放在代码块的头部。
// 等同于
var x;
if (!x) {
x = {};
}
//----------------------------------------------
for (var i = 0; i < 10; i++) {
// ...
}
// 写成
var i;
for (i = 0; i < 10; i++) {
// ...
}
//所有函数都应该在使用之前定义。函数内部的变量声明,都应该放在函数的头部。
25.7 with 语句
with
可以减少代码的书写,但是会造成混淆。
with (o) {
foo = bar;
}
//-------------------
//这四种结果都可能发生,取决于不同的变量是否有定义。因此,不要使用with语句。
o.foo = bar;
o.foo = o.bar;
foo = bar;
foo = o.bar;
25.8 相等和严格相等
JavaScript 有两个表示相等的运算符:“相等”(==
)和“严格相等”(===
)。
0 == ''// true
1 == true // true
2 == true // false
0 == '0' // true
false == 'false' // false
false == '0' // true
' \t\r\n ' == 0 // true
//建议不要使用相等运算符(==),只使用严格相等运算符(===)。
25.9 语句的合并
建议不要将不同目的的语句,合并成一行。
a = b;
if (a) {
// ...
}
//写成
if (a = b) {
// ...
}
25.10自增和自减运算符
自增(++
)和自减(--
)运算符,放在变量的前面或后面,返回的值不一样,很容易发生错误。事实上,所有的++
运算符都可以用+= 1
代替。
++x
// 等同于
x += 1;
//建议自增(++)和自减(--)运算符尽量使用+=和-=代替。
25.11 switch…case 结构
switch...case
结构要求,在每一个case
的最后一行必须是break
语句,否则会接着运行下一个case
。这样不仅容易忘记,还会造成代码的冗长。
而且,switch...case
不使用大括号,不利于代码形式的统一。此外,这种结构类似于goto
语句,容易造成程序流程的混乱,使得代码结构混乱不堪,不符合面向对象编程的原则。
function doAction(action) {
switch (action) {
case 'hack':
return 'hack';
case 'slash':
return 'slash';
case 'run':
return 'run';
default:
throw new Error('Invalid action.');
}
}
//---------------------改为-----------------------
function doAction(action) {
var actions = {
'hack': function () {
return 'hack';
},
'slash': function () {
return 'slash';
},
'run': function () {
return 'run';
}
};
if (typeof actions[action] !== 'function') {
throw new Error('Invalid action.');
}
return actions[action]();
}