Быстрые советы, которые сделают ваш код удобочитаемым и поддерживаемым.

Сколько раз вы открывали старый проект, чтобы найти запутанный код, который легко ломается, когда вы добавляете в него что-то новое? Мы все были там.

В надежде уменьшить количество нечитаемых JavaScript в мире, я представляю вам следующие примеры. Во всем в чем я был виноват в прошлом.

Использование деструктуризации массива для функций с множественными возвращаемыми значениями

Предположим, у нас есть функция, которая возвращает несколько значений. Одна из возможных реализаций - использовать деструктуризацию массива следующим образом:

const func = () => {
  const a = 1;
  const b = 2;
  const c = 3;
  const d = 4; 
  return [a,b,c,d];
}
const [a,b,c,d] = func();
console.log(a,b,c,d); // Outputs: 1,2,3,4

Хотя описанный выше подход работает нормально, он вносит некоторые сложности.

Когда мы вызываем функцию и присваиваем значения a,b,c,d, мы должны быть внимательны к порядку, в котором возвращаются данные. Небольшая ошибка здесь может стать кошмаром для дальнейшей отладки.

Кроме того, невозможно точно указать, какие значения мы хотели бы получить от функции. Что, если нам нужны только c и d?

Вместо этого мы можем использовать деструктуризацию объекта.

const func = () => {
  const a = 1;
  const b = 2;
  const c = 3;
  const d = 4;
  return {a,b,c,d};
}
const {c,d} = func();

Теперь мы можем легко выбрать нужные нам данные из функции.

Это также защищает наш код от будущего, позволяя нам со временем добавлять дополнительные возвращаемые переменные, не нарушая работу.

Не использовать деструктуризацию объекта для параметров функции

Предположим, у нас есть функция, которая принимает объект в качестве аргумента и выполняет некоторую операцию со свойствами объекта. Наивный подход может выглядеть примерно так:

// bad
function getDaysRemaining(subscription) {
  const startDate = subscription.startDate;
  const endDate = subscription.endDate;
  return endDate - startDate;
}

Вышеупомянутый подход работает по назначению, однако мы создаем две ненужные временные ссылки startDate и endDate.

В лучшей реализации используется деструктуризация объекта subscription для получения startDate и endDate в одной строке.

// better
function getDaysRemaining(subscription) {
  const { startDate, endDate } = subscription;
  return startDate - endDate;
}

Мы можем сделать еще один шаг вперед, выполнив деструктуризацию объекта непосредственно на аргументе.

// even better
function getDaysRemaining({ startDate, endDate }) {
  return startDate - endDate;
}

Гораздо элегантнее, не могли бы вы согласиться?

Копирование массивов без использования оператора распространения

Использование for-loop для перебора массива и копирования его элементов в новый массив многословно и довольно некрасиво.

Оператор распространения может быть использован с тем же эффектом в ясной и лаконичной манере.

const stuff = [1,2,3];
// bad
const stuffCopyBad = []
for(let i = 0; i < stuff.length; i++){
  stuffCopyBad[i] = stuff[i];
}
// good
const stuffCopyGood = [...stuff];

Использование Var

Использование const гарантирует, что переменную нельзя переназначить. Это уменьшает количество ошибок в нашем коде и упрощает понимание.

// bad
var x = "badX";
var y = "baxY";
// good
const x = "goodX";
const y = "goodX";

Если вам действительно нужно переназначить переменную, всегда отдавайте предпочтение let, а не var.

Это потому, что let имеет область видимости блока, тогда как var - область видимости функции.

Блочная область видимости говорит нам, что к переменной можно получить доступ только внутри блока кода, в котором она определена. Попытка получить доступ к переменной вне блока дает нам ReferenceError.

for(let i = 0; i < 10; i++){
  //something
}
print(i) // ReferenceError: i is not defined

Функция в области видимости сообщает нам, что к переменной можно получить доступ только внутри функции, в которой она определена.

for(var i = 0; i < 10; i++){
  //something
}
console.log(i) // Outputs 10

Оба let и const имеют блочную область видимости.

Не использовать шаблонные литералы

Объединение строк вручную довольно громоздко для набора и может сбивать с толку при чтении. Вот пример:

// bad
function printStartAndEndDate({ startDate, endDate }) {
  console.log('StartDate:' + startDate + ',EndDate:' + endDate)
}

Литералы шаблона предоставляют нам понятный и лаконичный синтаксис, который поддерживает интерполяцию строк.

// good
function printStartAndEndDate({ startDate, endDate }) {
  console.log(`StartDate: ${startDate}, EndDate: ${endDate}`)
}

Литералы шаблона также позволяют легко вставлять новые строки. Все, что вам нужно сделать, это нажать клавишу ввода на клавиатуре, как обычно.

// prints on two lines
function printStartAndEndDate({ startDate, endDate }) {
  console.log(`StartDate: ${startDate}
  EndDate: ${endDate}`)
}

Заключительные слова

Спасибо за прочтение!

Если я пропустил что-то очевидное, оставьте отзыв, и я проверю.