Michael Wanyoike , Sam Deering가 저술한 Sitepoint의 아티클을 번역하였습니다. 원문보러가기


자바스크립트 기반 개발자라면 꼭 읽어보세요. 제가 수년간 자바스크립트 개발을 하며 익힌 축약코딩 기술들에 대한 리퍼런스로 사용하기 위해 이 아티클을 작성하였습니다. 축약코딩이 익숙하지 않은 분들이 코드의 흐름을 파악하기 쉽게하기 위하여 일반 코딩 기법으로도 샘플을 작성해 놓았습니다.

2017년 6월 14일: ES6에 대응하는 축약코딩 기법을 추가하기위해 업데이트 되었습니다. ES6에 대해서 더 알고싶으시다면 SitePoint 프리미엄을 가입하시고 A Look into ES6 스크린케스트를 확인해보세요.

1. 삼항조건 연산자 (The Ternary Operator)

if..else 문항을 사용할때 한줄로 줄여주는 아주 좋은 방법입니다.
기존:

const x = 20;
let answer;
if (x > 10) {
    answer = 'greater than 10';
} else {
    answer = 'less than 10';
}

축약기법:

const answer = x > 10 ? 'greater than 10' : 'less than 10';

이렇게도 사용할 수 있습니다:

const answer = x > 10 ? " greater than 10" : x 

역주

// 리액트에서 특정 버튼을 state값에 따라 나타나게 할경우 이렇게 사용할 수 있습니다.
{editable ? (
    <a onClick={() => this.save(record.key)}>확인</a>
) : (
    <a onClick={() => this.edit(record.key)}>수정</a>
)} 

2. 간략계산법 (Short-circuit Evaluation)

기존의 변수를 다른 변수에 할당하고 싶은 경우, 기존 변수가 null, undefined 또는 empty 값이 아닌것을 확인해야합니다. (위 세가지일 경우 에러가 뜹니다) 이를 해결하기 위해서 긴 if문을 작성하거나 축약코딩으로 한줄에 끝낼 수 있습니다!
기존:

if (variable1 !== null || variable1 !== undefined || variable1 !== '') {
     let variable2 = variable1;
}

축약기법:

const variable2 = variable1  || 'new';

진짜 이게 끝이냐구요? es6console에 아래 코드를 입력해서 확인해보세요.


let variable1;
let variable2 = variable1  || '';
console.log(variable2 === ''); // prints true

variable1 = 'foo';
variable2 = variable1  || '';
console.log(variable2); // prints foo

3. 변수 선언

함수를 시작하기 전 먼저 필요한 변수들을 선언하는건 현명한 코딩 방법입니다. 축약기법을 사용하면 여러개의 변수를 더 효과적으로 선언함으로 시간과 코딩 스페이스를 줄일 수 있습니다.
기존:

let x;
let y;
let z = 3;

축약기법:

let x, y, z=3;

4. If Presence

크게 중요한건 아니지만, 이 방법도 알려드리면 좋을거 같습니다. if문을 확인하기 위해서는, 대입 연산자를 제외하고 작성 할 수 있습니다.
기존:

if (likeJavaScript === true)

축약기법:

if (likeJavaScript)

Note: 위 두개의 예제는 정확히 일치하지는 않습니다. 축약기법의 if 문은 likeJavaScript 값이 truthy일 경우 통과하도록 되어있지만, 기존 방법은 무조건 TRUE 일경우에만 통과할 수 있기 때문입니다.

다음 예제입니다. 만일 a 값이 true 가 아닐경우, 특정 코드를 실행합니다.
기존:

let a;
if ( a !== true ) {
// 코드 실행...
}

축약기법:

let a;
if ( !a ) {
// 코드실행...
}

5. For 루프

For 문을 돌릴때 jQuery나 lodash 같은 라이브러리에 의존하지 않고 바닐라 자바스크립트만을 사용하고 싶다면 이 팁은 아주 유용하겠습니다.
기존:

for (let i = 0; i < allImgs.length; i++)

축약기법:

for (let index of allImgs)

Array.forEach 축약기법:

function logArrayElements(element, index, array) {
  console.log("a[" + index + "] = " + element);
}
[2, 5, 9].forEach(logArrayElements);
// logs:
// a[0] = 2
// a[1] = 5
// a[2] = 9

6. 간략 계산법 (Short-circuit Evaluation)

기본 값을 부여하기 위해 파라미터의 null 또는 undefined 여부를 파악하느라 6줄 이상의 코드를 작성하는것보다 short-circuit evaluation 방법을 이요해서 한줄로 작성하는 방법이 있습니다.
기존:

let dbHost;
if (process.env.DB_HOST) {
  dbHost = process.env.DB_HOST;
} else {
  dbHost = 'localhost';
}

축약기법:

const dbHost = process.env.DB_HOST || 'localhost';

역주: Short-circuit evaluation 이란?
두가지의 변수를 비교할때, 앞에 있는 변수가 false 일경우 결과는 무조건 false 이기때문에 뒤의 변수는 확인하지 않고 return 시키는 방법.
위의 예제에서는 process.env.DB_HOST 값이 있을경우 dbHost 변수에 할당하지만, 없으면 localhost 를 할당합니다. (짱죠하)

7. 십진수 지수 (Decimal base exponents)

0이 많은 숫자를 적을때, 수 많은 0들을 제외하고 코딩을 하게 된다면 간지나지 않을까요? 예를 들어 1e7은 1 뒤에 0이 7개 붙는다는 뜻입니다. 이는 10,000,000를 줄여쓴 것이고 자바스크립트에서는 float 타입값으로 받아드립니다.

기존:

for (let i = 0; i < 10000; i++) {}

축약기법:

for (let i = 0; i < 1e7; i++) {}

// All the below will evaluate to true
1e0 === 1;
1e1 === 10;
1e2 === 100;
1e3 === 1000;
1e4 === 10000;
1e5 === 100000;

8. 객체 프로퍼티

객체 리터럴 표기법은 자바스크립트 코딩을 훨씬 쉽게 만들어줍니다. 하지만 ES6는 더 쉬운 방법을 제안하죠. 만일 프로퍼티 이름이 key 이름과 같을경우, 축약기법을 활용할 수 있습니다.

기존:

const obj = { x:x, y:y };

축약기법:

const obj = { x, y };

9. 애로우(화살표) 함수

기존 함수 선언문은 읽고, 쓰기 쉽게 되어있습니다. 하지만 함수 네스팅이 시작되면 선언문 자체가 불필요하게 느껴지고, 헷갈리게 됩니다.

기존:

function sayHello(name) {
  console.log('Hello', name);
}

setTimeout(function() {
  console.log('Loaded')
}, 2000);

list.forEach(function(item) {
  console.log(item);
});

축약기법:

sayHello = name => console.log('Hello', name);

setTimeout(() => console.log('Loaded'), 2000);

list.forEach(item => console.log(item));

애로우 함수 표기법에서는 this가 기존의 함수 선언문과 다르게 받아들여집니다. 따라서 위의 두 예제는 완벽하게 동일하다고 볼 수는 없습니다. 이에 대해 더 알고 싶으시다면 이 아티클을 참고하세요.

10. 묵시적 반환(Implicit Return)

return 은 함수 결과를 반환하는데 사용되는 명령어 입니다. 한 줄로만 작성된 애로우 함수는 별도의 return 명령어가 없어도 자동으로 반환하도록 되어있습니다. 다만, 중괄호({})를 생략한 함수여야 return 명령어도 생략 할 수 있습니다.

한 줄 이상의 문장(객체 리터럴)을 반환하려면 중괄호({})대신 괄호(())를 사용해서 함수를 묶어야합니다. 이렇게 하면 함수가 한 문장으로 작성되었음을 나타낼 수 있습니다.

기존:

function calcCircumference(diameter) {
  return Math.PI * diameter
}

축약기법:

calcCircumference = diameter => (
  Math.PI * diameter;
)

11. 파라미터 기본 값 지정하기(Default Parameter Values)

기존에는 if 문을 통해서 함수의 파라미터 값에 기본 값을 지정해줘야했습니다. ES6 에서는 함수 선언문 자체에서 기본값을 지정해 줄 수 있습니다.

기존:

function volume(l, w, h) {
  if (w === undefined)
    w = 3;
  if (h === undefined)
    h = 4;
  return l * w * h;
}

축약기법:

volume = (l, w = 3, h = 4 ) => (l * w * h);
volume(2) //output: 24

12. 템플릿 리터럴 (Template Literals)

문자열로 ' + ' 를 입력하며 자바스크립트 값을 추가하는 손가락 노동에 지치지 않나요? ES6 에서는 이보다 훨씬 쉬운 방법이 있습니다. 사용 방법은 백틱(backtick) 을 사용해서 스트링을 감싸고, ${}를 사용해서 변수를 담아주면 됩니다.

기존:

const welcome = 'You have logged in as ' + first + ' ' + last + '.'

const db = 'http://' + host + ':' + port + '/' + database;

축약기법:

const welcome = `You have logged in as ${first} ${last}`;

const db = `http://${host}:${port}/${database}`;

13. 비구조화 할당 (Destructuring Assignment)

유명한 프레임워크로 개발을 하고 있다면 컴포넌트와 API간 정보를 전송하기 위해서 객체 리터럴이나 배열로 이뤄진 데이터를 사용하게 될 가능성이 큽니다. 데이터 객체가 컴포넌트에 들어가게 되면, unpack 이 필요합니다.

기존:

const observable = require('mobx/observable');
const action = require('mobx/action');
const runInAction = require('mobx/runInAction');

const store = this.props.store;
const form = this.props.form;
const loading = this.props.loading;
const errors = this.props.errors;
const entity = this.props.entity;

축약기법:

import { observable, action, runInAction } from 'mobx';

const { store, form, loading, errors, entity } = this.props;

축약기법으로 커스텀 변수명을 지정할 수 있습니다:

const { store, form, loading, errors, entity:contact } = this.props;

14. 여러줄로 문자열 쓰기 (Multi-line String)

한 줄 이상의 문자열을 입력하게 될 경우가 있다면 기존의 방법보다 훨씬 편한 방법이 있습니다.

기존:

const lorem = 'Lorem ipsum dolor sit amet, consectetur\n\t'
    + 'adipisicing elit, sed do eiusmod tempor incididunt\n\t'
    + 'ut labore et dolore magna aliqua. Ut enim ad minim\n\t'
    + 'veniam, quis nostrud exercitation ullamco laboris\n\t'
    + 'nisi ut aliquip ex ea commodo consequat. Duis aute\n\t'
    + 'irure dolor in reprehenderit in voluptate velit esse.\n\t'

이런 방법으로 개발을 해왔겠지만, 백틱(backtick) 을 사용하는 방법도 있습니다.

축약기법:

const lorem = `Lorem ipsum dolor sit amet, consectetur
    adipisicing elit, sed do eiusmod tempor incididunt
    ut labore et dolore magna aliqua. Ut enim ad minim
    veniam, quis nostrud exercitation ullamco laboris
    nisi ut aliquip ex ea commodo consequat. Duis aute
    irure dolor in reprehenderit in voluptate velit esse.`

15. 전개 연산자 (Spread Operator)

ES6에서 소개된 전개 연산자는 자바스크립트 코드를 더 효율적이고 재미있게 사용 할 수 있는 방법을 제시합니다. 간단히는 배열의 값을 변환하는데 사용할 수 있습니다. 전개 연산자를 사용하는 방법은 점 세개(...)를 붙이면 됩니다.

기존:

// joining arrays
const odd = [1, 3, 5];
const nums = [2 ,4 , 6].concat(odd);

// cloning arrays
const arr = [1, 2, 3, 4];
const arr2 = arr.slice()

축약기법:

// joining arrays
const odd = [1, 3, 5 ];
const nums = [2 ,4 , 6, ...odd];
console.log(nums); // [ 2, 4, 6, 1, 3, 5 ]

// cloning arrays
const arr = [1, 2, 3, 4];
const arr2 = [...arr];

concat()함수와는 다르게 전개 연산자를 이용하면 하나의 배열을 다른 배열의 아무 곳에나 추가할 수 있습니다.

const odd = [1, 3, 5 ];
const nums = [2, ...odd, 4 , 6];

전개 연산자는 ES6의 구조화 대입법(destructuring notation)와 함께 사용할 수도 있습니다.

const { a, b, ...z } = { a: 1, b: 2, c: 3, d: 4 };
console.log(a) // 1
console.log(b) // 2
console.log(z) // { c: 3, d: 4 }

16. 필수(기본) 파라미터 (Mandatory Parameter)

기본적으로 자바스크립트는 함수의 파라미터값을 받지 않았을경우, undefined로 지정합니다. 다른 언어들은 경고나 에러 메시지를 나타내기도 하죠. 이런 기본 파라미터 값을 강제로 지정하는 방법은 if 문을 사용해서 undefined일 경우 에러가 나도록 하거나, ‘Mandatory parameter shorthand’을 사용하는 방법이 있습니다.

기존:

function foo(bar) {
  if(bar === undefined) {
    throw new Error('Missing parameter!');
  }
  return bar;
}

축약기법:

mandatory = () => {
  throw new Error('Missing parameter!');
}

foo = (bar = mandatory()) => {
  return bar;
}

17. Array.find

자바스크립트로 특정 값을 찾기 위한 함수를 작성하다보면 보통 for 루프를 이용해서 작성을 하게 됩니다. ES6에서는 find()라는 새로운 함수가 생겼습니다.

기존:

const pets = [
  { type: 'Dog', name: 'Max'},
  { type: 'Cat', name: 'Karl'},
  { type: 'Dog', name: 'Tommy'},
]

function findDog(name) {
  for(let i = 0; i<pets.length; ++i) {
    if(pets[i].type === 'Dog' && pets[i].name === name) {
      return pets[i];
    }
  }
}

축약기법:

pet = pets.find(pet => pet.type ==='Dog' && pet.name === 'Tommy');
console.log(pet); // { type: 'Dog', name: 'Tommy' }

18. Object [key]

Foo.bar 를 Foo[‘bar’] 로 적을 수 있는걸 알고 있나요? 왜 후자와 같이 코딩을 해야하는지 의문이 들 수도 있겠지만, 재사용이 용이한 코드 블락을 작성하기 위해서는 매우 효율적인 방법입니다.

아래의 간단한 validation 함수 예시를 확인해보세요:

function validate(values) {
  if(!values.first)
    return false;
  if(!values.last)
    return false;
  return true;
}

console.log(validate({first:'Bruce',last:'Wayne'})); // true

위 함수로 validation기능을 완벽하게 사용할 수 있습니다. 하지만 form 요소들과 validation 옵션으로 사용해야하는 영역과 규칙(fields and rules) 이 많을 경우 위의 함수는 점점 복잡해지고 길어지게 됩니다. 이를 방지하기 위해서 실행시 옵션을 부과할 수 있는 포괄적인 validation 함수를 작성하는 방법을 알아보겠습니다.

축약기법:


// object validation rules (객체로 만든 validation 규칙)
const schema = {
  first: {
    required:true
  },
  last: {
    required:true
  }
}

// universal validation function (공통적으로 사용할 수 있는 validation 함수)
const validate = (schema, values) => {
  for(field in schema) {
    if(schema[field].required) {
      if(!values[field]) {
        return false;
      }
    }
  }
  return true;
}

console.log(validate(schema, {first:'Bruce'})); // false
console.log(validate(schema, {first:'Bruce',last:'Wayne'})); // true

위 예시처럼 사용한다면 모든 form에 공통으로 적용시킬 수 있는 validation 함수를 작성할 수 있습니다.

19. 단항 비트 논리부정 연산자 (Double Bitwise NOT)

비트 연산자는 자바스크립트 공부를 시작하면서 한번 배운뒤 한번도 적용해본적 없는 연산자일 겁니다. 애당초 이진법으로 코딩하지 않는다면 1 과 0 을 사용 할 일이 없죠.

하지만 이번 팁은 단항 비트 논리부정 연산자를 효율적으로 사용할 수 있는 방법을 알려드립니다. 바로 Math.floor() 함수의 대체용으로 사용할 수 있다는 것이죠. 또 Math.floor() 함수보다 훨씬 빠르게 작동한다는 장점도 있습니다. 단항 비트 논리부정 연산자에 대해서는 여기에서 더 알아보실 수 있습니다.

기존:

Math.floor(4.9) === 4  //true

축약기법:

~~4.9 === 4  //true

20. 다른 팁을 추천해주세요

원작자의 글: I really do love these and would love to find more, please leave a comment!
원문보러가기


사족: 개인적으로 꼭 알아둬야하는 ES6 축약기법들이라고 생각해서 번역을 해봤습니다. 군데군데 번역이 이상한 부분이 있을 수 있습니다(ㅇㅅㅇ). 잘못된 부분은 댓글로 알려주시면 감사하겠습니다!