常见 JavaScript 代码风格对比

工具相关 ·

JavaScript 社区存在多种代码风格,从缩进到分号,从引号到逗号,每个选择都有支持者。本文将客观对比常见风格,帮助团队做出选择。

缩进风格

Tab vs 空格

// Tab 缩进
function greet(name) {
→   return 'Hello, ' + name;
}

// 空格缩进(4 空格)
function greet(name) {
    return 'Hello, ' + name;
}
方面Tab空格
文件大小更小稍大
跨编辑器一致性取决于设置始终一致
可访问性可自定义宽度固定宽度
社区主流少数多数

建议:选择空格,因为跨平台一致性更重要。

2 空格 vs 4 空格

// 2 空格(React/Vue 社区主流)
function greet(name) {
  return 'Hello, ' + name;
}

// 4 空格(传统 JS 社区主流)
function greet(name) {
    return 'Hello, ' + name;
}
方面2 空格4 空格
横向空间更多代码可见较少代码可见
嵌套清晰度稍弱更强
流行框架React, Vue, AngularjQuery, Node.js

建议:跟随团队或项目的主流选择。

引号风格

单引号 vs 双引号

// 单引号
const name = 'test';
const html = '<div class="box">content</div>';

// 双引号
const name = "test";
const html = "<div class=\"box\">content</div>";
方面单引号双引号
输入便利性不需要 Shift需要 Shift
HTML 内嵌不需要转义需要转义
JSON 兼容性需要转换原生支持
社区主流JS 社区JSON/HTML

建议:JS 代码用单引号,JSON 用双引号(规范要求)。

分号使用

有分号 vs 无分号

// 有分号
const name = 'test';
function greet() {
    return 'hello';
}

// 无分号(Standard 风格)
const name = 'test'
function greet() {
    return 'hello'
}

ASI(自动分号插入)陷阱:

// 危险代码
const a = 1
const b = 2
[a, b].forEach(console.log)  // 报错!

// 解释为:
const b = 2[a, b].forEach(console.log)
// 2[2, 1] 是 undefined,undefined.forEach 报错

// 修复:无分号风格需要在行首加 ;
;[a, b].forEach(console.log)
方面有分号无分号
安全性无 ASI 问题需要注意陷阱
代码简洁多一个字符更简洁
社区主流多数项目Standard/Vue

建议:使用分号,避免潜在的 ASI 问题。

大括号风格

K&R vs Allman

// K&R(同行)
if (condition) {
    doSomething();
} else {
    doOther();
}

// Allman(换行)
if (condition)
{
    doSomething();
}
else
{
    doOther();
}
方面K&RAllman
行数更少更多
可读性紧凑清晰
JS 社区主流少数
C#/C++少数主流

建议:JS 使用 K&R 风格,这是社区惯例。

尾逗号

有尾逗号 vs 无尾逗号

// 有尾逗号
const obj = {
    name: 'test',
    age: 18,
};

const arr = [
    1,
    2,
    3,
];

// 无尾逗号
const obj = {
    name: 'test',
    age: 18
};
方面有尾逗号无尾逗号
Git diff更清晰多一行改动
添加新项方便需要修改上一行
兼容性ES5+所有环境

建议:使用尾逗号(es5 模式),Git diff 更友好。

箭头函数

单行 vs 多行

// 单行(隐式返回)
const double = x => x * 2;
const sum = (a, b) => a + b;

// 多行(显式返回)
const process = (data) => {
    const filtered = data.filter(x => x > 0);
    return filtered.map(x => x * 2);
};

建议:

  • 简单逻辑用单行箭头函数
  • 超过 3 行用多行形式

命名风格

变量和函数

// camelCase(主流)
const userName = 'test';
function getData() { }

// snake_case(少数)
const user_name = 'test';
function get_data() { }

// PascalCase(类/组件)
class UserService { }
function UserProfile() { }

建议:变量/函数用 camelCase,类/组件用 PascalCase。

导入顺序

// 推荐:分组排序
// 1. Node.js 内置模块
import fs from 'fs';
import path from 'path';

// 2. 第三方库
import React from 'react';
import axios from 'axios';

// 3. 内部模块(别名路径)
import { API_URL } from '@/config';
import UserService from '@/services/UserService';

// 4. 相对路径
import { formatDate } from './utils';
import styles from './App.module.css';

// 5. 样式文件
import './global.css';

注释风格

// 单行注释
const value = 42;  // 魔法数字

// 多行注释
/*
 * 这是一个复杂的算法
 * 用于处理特殊情况
 */
function complexAlgorithm() { }

// JSDoc
/**
 * 获取用户信息
 * @param {string} id - 用户 ID
 * @returns {Promise<User>} 用户信息
 */
async function getUser(id) { }

// TODO/FIXME
// TODO: 添加错误处理
// FIXME: 在 Safari 下有兼容性问题

风格配置推荐

Prettier 配置

{
    "semi": true,
    "singleQuote": true,
    "tabWidth": 4,
    "trailingComma": "es5",
    "printWidth": 100,
    "bracketSpacing": true,
    "arrowParens": "avoid"
}

ESLint 配置

{
    "extends": [
        "eslint:recommended",
        "prettier"
    ],
    "rules": {
        "no-var": "error",
        "prefer-const": "error",
        "eqeqeq": ["error", "always"],
        "curly": ["error", "multi-line"]
    }
}

总结

代码风格没有绝对的对错,但团队统一很重要。选择一个主流风格,使用工具自动化,让开发者专注于逻辑而非格式。

阅读 16