JavaScript 最佳实践:提升代码质量与安全性

作者:沉舟

时间:2026-10-30

浏览:587

本文介绍 JavaScript 开发中的关键最佳实践,包括避免全局变量污染、正确使用严格模式、使用严格相等运算符、利用逻辑运算符简化代码以及遵循代码风格指南。通过掌握这些技巧,开发者可以编写更安全、高效且易于维护的 JavaScript 代码。

文章目录

持续学习新事物能助理性之人成就非凡。对于开发人员而言,不断学习是工作的核心部分,无论这些新知识是否源于积极的学习体验。

本教程将介绍若干重要的 JavaScript 最佳实践,帮助你避免通过试错来掌握它们。准备好提升你的代码质量吧!

1. 避免对全局作用域的污染

1. 避免对全局作用域的污染

声明变量看似简单,但有时即便你无意为之,也可能意外创建全局变量。在现代浏览器中,全局变量均存储在 window 对象内。由于该对象内容庞大,你极有可能覆盖某些默认值。

假设你有一个 HTML 文件,其中包含一个 <script> 标签,该标签内嵌(或通过引用 JavaScript 文件加载)以下内容:


var foo = 42;
console.log(foo);

这段代码显然会输出 42。但由于代码并非在函数内执行,其执行上下文为全局上下文。因此,变量会被附加到 window 对象上。这意味着 window.foo 的值也将是 42。

这存在风险,因为你可能覆盖已存在的全局变量:


function print () {
  // do something
}
print();

当执行 window.print(或仅执行 print)时,它不会打开打印弹窗,因为我们已覆盖了原生的打印逻辑。

解决此问题的方案相当简单:我们需要一个定义后立即调用的闭包函数,如下所示:


// Declare an anonymous function
(function () {
  var foo = 42;
  console.log(window.foo);
  // → undefined
  console.log(foo);
  // → 42
})();
//^ and call it immediately

或者,你也可以选择将 window 及其他全局对象(如 document)作为参数传递给该函数(这或许能提升性能):


(function (global, doc) {
 global.setTimeout(function () {
   doc.body.innerHTML = "Hello!";
 }, 1000);
})(window, document);

因此,你应使用闭包函数来避免创建全局变量。注意,此处为了聚焦代码本身,后续代码片段中不再使用闭包函数。

提示:browserify 是避免创建全局变量的另一种方式。它采用你在 Node.js 中同样会使用的 require 函数机制。

顺便一提,Node.js 会自动将你的文件封装进函数中。它们看起来如下:


(function (exports, require, module, __filename, __dirname) {
// ...

因此,如果你认为 require 函数是全局的,那并不准确。它仅仅是函数的一个参数。

你知道吗?

由于 window 对象包含所有全局变量,且它自身也是全局的,因此 window 内部引用了它自己:


window.window.window
// => Window {...}

这表明 window 对象是一个循环引用对象。下面展示了如何创建这样的对象:


// Create an object
var foo = {};
// Point a key value to the object itself
foo.bar = foo;
// The `foo` object just became a circular one:
foo.bar.bar.bar.bar
// → foo

或者,为了展示你对 JavaScript 的无限热爱,你可以像发烧友那样操作,代码如下:

1. 避免对全局作用域的污染

是的,你可以近乎无限地展开这个对象(也可能导致浏览器崩溃)。

2. 好的 use strict 使用习惯

务必使用 use strict!这只需在代码中添加一行,为你的脚本增加更多保障。

例如:


// This is bad, since you do create a global without having anyone to tell you
(function () {
   a = 42;
   console.log(a);
   // → 42
})();
console.log(a);
// → 42

使用 use strict,你可以获得更详细的错误信息:


(function () {
   "use strict";
   a = 42;
   // Error: Uncaught ReferenceError: a is not defined
})();

你可能会好奇为何可以将 "use strict" 放在封装函数外部。这确实可行,但它会应用于全局范围。这并非最坏情况,但如果代码来自其他库或将所有内容打包到一个文件中时,这样做会产生影响。

3. 严格相等

这一点很简单。如果你在 JavaScript 中使用 == 比较 a 和 b(像其他编程语言那样),可能会发现其行为有些奇怪:如果你有一个字符串和一个数字,它们会相等(==):


"42" == 42
// → true

出于明显原因(例如验证操作),最好使用严格等于(===):


"42" === 42
// → false

4. 使用 && 和 || 来制造点小把戏

根据你的需求,你可以使用逻辑运算符使代码更简洁。

取默认值


"" || "foo"
// → "foo"
undefined || 42
// → 42
// Note that if you want to handle 0 there, you need
// to check if a number was provided:
var a = 0;
a || 42
// → 42
// This is a ternary operator—works like an inline if-else statement
var b = typeof a === "number" ? a : 42;
// → 0

无需使用 if 表达式检查某物是否为真,你也可以简单地这样做:


expr && doSomething();

// Instead of:

if (expr) {
   doSomething();
}

如果你需要通过 doSomething() 来决定返回结果,这样做更酷:


function doSomething () {
   return { foo: "bar" };
}

var expr = true;

var res = expr && doSomething();
res && console.log(res);
// → { foo: "bar" }

你可能不赞同我的观点,但正如我所说,这样做效果更佳。如果你不想让代码看起来如此混淆,但这正是那些 JavaScript 简化器实际会做的事情。

在我看来,这样做虽然让代码更简短,但仍具可读性。

5. 对值的类型进行转化

有几种方法可根据你的想法进行转化。最常用的方式如下:


// From anything to a number

var foo = "42";
var myNumber = +foo; // shortcut for Number(foo)
// → 42

// Tip: you can convert it directly into a negative number
var negativeFoo = -foo; // or -Number(foo)
// → -42

// From object to array
// Tip: `arguments` is an object and in general you want to use it as array
var args = { 0: "foo", 1: "bar", length: 2 };
Array.prototype.slice.call(args)
// → [ 'foo', 'bar' ]

// Anything to boolean
/// Non non p is a boolean p
var t = 1;
var f = 0;
!!t
// → true
!!f
// → false

/// And non-p is a boolean non-p
!t
// → false
!f
// → true

// Anything to string
var foo = 42;
"" + foo // shortcut for String(foo)
// → "42"

foo = { hello: "world" };
JSON.stringify(foo);
// → '{ "hello":"world" }'

JSON.stringify(foo, null, 4); // beautify the things
// →
// '{
//    "hello": "world"
// }'

// Note you cannot JSON.stringify circular structures
JSON.stringify(window);
// ⚠ TypeError: JSON.stringify cannot serialize cyclic structures.

6. 代码风格/风格指南

在新项目中,确保所有文件遵循相同的代码风格。对于现有项目,沿用现有的代码风格,除非你决定改变它(提示:就此与你的搭档讨论)。即使你要创建并记录自己的代码风格,也应始终遵循它。

现有的一些不同代码风格如下:

  • Google JavaScript 风格指南

  • airbnb/javascript

  • ... 也还有其它的一些

  • 我的风格指南

额外的福利小提示:

你应该记住的其他一些重要的 JavaScript 最佳实践是那些能帮助你对代码进行格式化的工具。以下是其中一些:

  • js-beautify: 美化你的代码

  • UglifyJS(2): 混淆/最小化你的代码

  • jshint: 检测 JavaScript 代码中的错误或者潜在问题

  • jscs: 可以配置的样式指南检测器

最后一点:不要总是 console.log,要对你的代码进行调试。

祝你编程愉快!

原文地址:https://www.codementor.io/johnnyb/tutorials/javascript-best-practices-du107mvud

实用工具推荐

电子包浆

绿化、压缩、噪点和虚拟水印,自由调节做旧程度。

使用 ›
图片压缩

选择画质和输出格式,预览压缩前后的大小。

使用 ›
相关文章