博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JavaScript: 代码简洁之道
阅读量:5966 次
发布时间:2019-06-19

本文共 6301 字,大约阅读时间需要 21 分钟。

一、变量

1、用有意义且常用的单词命名变量

Bad:const yyyymmdstr = moment().format('YYYY/MM/DD'); Good:const currentDate = moment().format('YYYY/MM/DD');

2、保持统一

可能同一个项目对于获取用户信息,会有三个不一样的命名,应该保持统一。

Bad:  getUserInfo();  getClientData();  getCustomerRecord(); Good:  getUser() 

3、每个常量都该命名

可以用 buddy.js 或者 ESLint 检测代码中未命名的常量。

Bad:// 三个月之后你还能知道 86400000 是什么吗?setTimeout(blastOff, 86400000);Good:const MILLISECOND_IN_A_DAY = 86400000;setTimeout(blastOff, MILLISECOND_IN_A_DAY);

4、可描述

通过一个变量生成了一个新变量,也需要为这个新变量命名,也就是说每个变量当你看到他第一眼你就知道他是干什么的。

Bad:const ADDRESS = 'One Infinite Loop, Cupertino 95014';const CITY_ZIP_CODE_REGEX = /^[^,\\]+[,\\\s]+(.+?)\s*(\d{5})?$/;saveCityZipCode(ADDRESS.match(CITY_ZIP_CODE_REGEX)[1],                ADDRESS.match(CITY_ZIP_CODE_REGEX)[2]);Good:const ADDRESS = 'One Infinite Loop, Cupertino 95014';const CITY_ZIP_CODE_REGEX = /^[^,\\]+[,\\\s]+(.+?)\s*(\d{5})?$/;const [, city, zipCode] = ADDRESS.match(CITY_ZIP_CODE_REGEX) || [];saveCityZipCode(city, zipCode);

5、直接了当

bad

const locations = ['Austin', 'New York', 'San Francisco'];locations.forEach((l) => {  doStuff();  doSomeOtherStuff();  // ...  // ...  // ...  // 需要看其他代码才能确定 'l' 是干什么的。  dispatch(l);});

good

const locations = ['Austin', 'New York', 'San Francisco'];locations.forEach((location) => {  doStuff();  doSomeOtherStuff();  // ...  // ...  // ...  dispatch(location);});

4、避免无意义的前缀

如果创建了一个对象 car,就没有必要把它的颜色命名为 carColor。

Bad:  const car = {    carMake: 'Honda',    carModel: 'Accord',    carColor: 'Blue'  };  function paintCar(car) {    car.carColor = 'Red';  }Good:const car = {  make: 'Honda',  model: 'Accord',  color: 'Blue'};function paintCar(car) {  car.color = 'Red';}

5、使用默认值

Bad:function createMicrobrewery(name) {  const breweryName = name || 'Hipster Brew Co.';  // ...}Good:function createMicrobrewery(name = 'Hipster Brew Co.') {  // ...}

二、函数 

1、参数越少越好

如果参数超过两个,使用 ES2015/ES6 的解构语法,不用考虑参数的顺序。

Bad:function createMenu(title, body, buttonText, cancellable) {  // ...}Good:function createMenu({ title, body, buttonText, cancellable }) {  // ...}createMenu({  title: 'Foo',  body: 'Bar',  buttonText: 'Baz',  cancellable: true});

2、只做一件事情

这是一条在软件工程领域流传久远的规则。严格遵守这条规则会让你的代码可读性更好,也更容易重构。如果违反这个规则,那么代码会很难被测试或者重用。

Bad:function emailClients(clients) {  clients.forEach((client) => {    const clientRecord = database.lookup(client);    if (clientRecord.isActive()) {      email(client);    }  });}Good:function emailActiveClients(clients) {  clients    .filter(isActiveClient)    .forEach(email);}function isActiveClient(client) {  const clientRecord = database.lookup(client);      return clientRecord.isActive();}

3、顾名思义

看函数名就应该知道它是干啥的。

Bad:function addToDate(date, month) {  // ...}const date = new Date();// 很难知道是把什么加到日期中addToDate(date, 1);Good:function addMonthToDate(month, date) {  // ...}const date = new Date();addMonthToDate(1, date);

4、删除重复代码

很多时候虽然是同一个功能,但由于一两个不同点,让你不得不写两个几乎相同的函数。

要想优化重复代码需要有较强的抽象能力,错误的抽象还不如重复代码。所以在抽象过程中必须要遵循 SOLID 原则(SOLID 是什么?稍后会详细介绍)。

Bad:

function showDeveloperList(developers) {  developers.forEach((developer) => {    const expectedSalary = developer.calculateExpectedSalary();    const experience = developer.getExperience();    const githubLink = developer.getGithubLink();    const data = {      expectedSalary,      experience,      githubLink    };    render(data);  });}function showManagerList(managers) {  managers.forEach((manager) => {    const expectedSalary = manager.calculateExpectedSalary();    const experience = manager.getExperience();    const portfolio = manager.getMBAProjects();    const data = {      expectedSalary,      experience,      portfolio    };    render(data);  });}

Good:

function showEmployeeList(employees) {  employees.forEach(employee => {    const expectedSalary = employee.calculateExpectedSalary();    const experience = employee.getExperience();    const data = {      expectedSalary,      experience,    };    switch(employee.type) {      case 'develop':        data.githubLink = employee.getGithubLink();        break      case 'manager':        data.portfolio = employee.getMBAProjects();        break    }    render(data);  })}

5、对象设置默认属性

bad: const menuConfig = {  title: null,  body: 'Bar',  buttonText: null,  cancellable: true};function createMenu(config) {  config.title = config.title || 'Foo';  config.body = config.body || 'Bar';  config.buttonText = config.buttonText || 'Baz';  config.cancellable = config.cancellable !== undefined ? config.cancellable : true;}createMenu(menuConfig); Good:const menuConfig = {  title: 'Order',  // 'body' key 缺失  buttonText: 'Send',  cancellable: true};function createMenu(config) {  config = Object.assign({    title: 'Foo',    body: 'Bar',    buttonText: 'Baz',    cancellable: true  }, config);  // config 就变成了: {title: "Order", body: "Bar", buttonText: "Send", cancellable: true}  // ...}createMenu(menuConfig);

6、不要传 flag 参数

通过 flag 的 true 或 false,来判断执行逻辑,违反了一个函数干一件事的原则。

Bad:function createFile(name, temp) {  if (temp) {    fs.create(`./temp/${name}`);  } else {    fs.create(name);  }}Good:function createFile(name) {  fs.create(name);}function createFileTemplate(name) {  createFile(`./temp/${name}`)} 

7、避免副作用(第一部分)

函数接收一个值返回一个新值,除此之外的行为我们都称之为副作用,比如修改全局变量、对文件进行 IO 操作等。

当函数确实需要副作用时,比如对文件进行 IO 操作时,请不要用多个函数/类进行文件操作,有且仅用一个函数/类来处理。也就是说副作用需要在唯一的地方处理。

副作用的三大天坑:随意修改可变数据类型、随意分享没有数据结构的状态、没有在统一地方处理副作用。

Bad:// 全局变量被一个函数引用// 现在这个变量从字符串变成了数组,如果有其他的函数引用,会发生无法预见的错误。var name = 'Ryan McDermott';function splitIntoFirstAndLastName() {  name = name.split(' ');}splitIntoFirstAndLastName();console.log(name); // ['Ryan', 'McDermott'];Good:var name = 'Ryan McDermott';var newName = splitIntoFirstAndLastName(name)function splitIntoFirstAndLastName(name) {  return name.split(' ');}console.log(name); // 'Ryan McDermott';console.log(newName); // ['Ryan', 'McDermott'];

8、避免副作用(第二部分)

在 JavaScript 中,基本类型通过赋值传递,对象和数组通过引用传递。以引用传递为例:

假如我们写一个购物车,通过 addItemToCart() 方法添加商品到购物车,修改 购物车数组。此时调用 purchase() 方法购买,由于引用传递,获取的 购物车数组 正好是最新的数据。

看起来没问题对不对?

如果当用户点击购买时,网络出现故障, purchase() 方法一直在重复调用,与此同时用户又添加了新的商品,这时网络又恢复了。那么 purchase() 方法获取到 购物车数组 就是错误的。

为了避免这种问题,我们需要在每次新增商品时,克隆 购物车数组 并返回新的数组。

Bad:const addItemToCart = (cart, item) => {  cart.push({ item, date: Date.now() });};Good:const addItemToCart = (cart, item) => {  return [...cart, {item, date: Date.now()}]};

 

转载于:https://www.cnblogs.com/Nyan-Workflow-FC/p/10464431.html

你可能感兴趣的文章
通过jsp请求Servlet来操作HBASE
查看>>
Shell编程基础
查看>>
Shell之Sed常用用法
查看>>
3.1
查看>>
校验表单如何摆脱 if else ?
查看>>
<气场>读书笔记
查看>>
Centos下基于Hadoop安装Spark(分布式)
查看>>
3D地图的定时高亮和点击事件(基于echarts)
查看>>
mysql开启binlog
查看>>
设置Eclipse编码方式
查看>>
分布式系统唯一ID生成方案汇总【转】
查看>>
并查集hdu1232
查看>>
Mysql 监视工具
查看>>
从前后端分离到GraphQL,携程如何用Node实现?\n
查看>>
Linux Namespace系列(09):利用Namespace创建一个简单可用的容器
查看>>
博客搬家了
查看>>
Python中使用ElementTree解析xml
查看>>
jquery 操作iframe、frameset
查看>>
解决vim中不能使用小键盘
查看>>
jenkins权限管理,实现不同用户组显示对应视图views中不同的jobs
查看>>