jtk

【学習メモ】[Udemy] JavaScriptエンジニアのためのES6完全ガイド 勉強メモ その2

概要

【世界で 2 万人が受講】JavaScript エンジニアのための ES6 完全ガイド | Udemy を学習したのでメモしておきます。

その 1の続きです。

構文編

constlet

const - JavaScript | MDN let - JavaScript | MDN

変更される可能性がない場合(定数)はconst、変わる可能性がある場合はletを使う。

// var name = 'Taro';
// var job = 'Frontend Engineer';
// var hourlySalary = 4000;

// ES6
const name = "Taro";
let job = "Frontend Engineer";
let hourlySalary = 4000;

// 時間が経過したとして...
job = "Technical Director";
hourlySalary = 6000;

テンプレートリテラル

テンプレート文字列 - JavaScript | MDN

テンプレート文字列、テンプレートストリング ともいう。

ES5

function getMessage() {
  const year = new Date().getFullYear();
  return "今年は" + year + "年です。";
}
getMessage();

テンプレートリテラルを使った場合

function getMessage() {
  const year = new Date().getFullYear();
  return `今年は${year}年です。`; // ひとつのまとまりとしてわかりやすく文字列を表現
  // return `今年は${year+10}年です。`; // こういうこともできる
}
getMessage();

アロー関数

アロー関数 - JavaScript | MDN

ES5

const add = function(a, b) {
  return a + b;
};
add(1, 2);

アロー関数を使った場合

const add = (a, b) => {
  return a + b;
};
add(1, 2);

関数内に 1 個しか評価項目がない場合、中括弧、return を削除、1 行に省略することもできる

const add = (a, b) => a + b;
add(1, 2);

mapを使う場合の例 ES5

const numbers = [1, 2, 3];
numbers.map(function(number) {
  return 2 * number;
});

アロー関数を使った場合

const numbers = [1, 2, 3];
numbers.map(number => {
  return 2 * number;
});

// もしくは
numbers.map(number => 2 * number);

Lexical 'this'(レキシカル ディス)
記述する場所によってthisが決まる。.bindselfを使う必要がない。
※lexical = 語彙の、構文的な

const team = {
  members: ["Taro", "Hanako"],
  teamName: "ONE PROJECT TEAM",
  teamSummary: function() {
    // アロー関数を書く場所で囲っているthisがアロー関数内のthisになる。
    // この場合、this === team
    return this.members.map(member => {
      return `${member}は${this.teamName}の所属です。`; // このコールバックは別世界で実行されている
    });
  }
};
team.teamSummary();

オブジェクトリテラル

ES6 オブジェクトリテラルの拡張 - Qiita

ES5

function createMusicShop(inventory) {
  return {
    inventory: inventory,
    inventoryValue: function() {
      // 配列のpriceを足して合計を求める
      return this.inventory.reduce((total, music) => total + music.price, 0);
    },
    priceForTitle: function(title) {
      // タイトルに対応した価格を返す
      return this.inventory.find(music => music.title === title).price;
    }
  };
}

const inventory = [
  { title: "KESHIKI", price: 2500 },
  { title: "aiqing", price: 3000 }
];
const musicShop = createMusicShop(inventory);

musicShop.inventoryValue(); // 5500
("");
musicShop.priceForTitle("KESHIKI"); // 2500

ES6

function createMusicShop(inventory) {
  return {
    inventory, // オブジェクトのkeyとvalueが同じ場合は省略できる
    inventoryValue() {
      // ': function' を省略できる
      return this.inventory.reduce((total, music) => total + music.price, 0);
    },
    priceForTitle(title) {
      // ': function' を省略できる
      return this.inventory.find(music => music.title === title).price;
    }
  };
}

関数のデフォルト引数

デフォルト引数 - JavaScript | MDN

ES5

// デフォルトの引数をif文で記述する必要がある
function makeAjaxRequest(url, method) {
  if (!method) {
    method = "GET";
  }
  // ajaxリクエストをするロジックがここにあると想定
  // ...
  return method;
}

makeAjaxRequest("google.com"); // methodがGETになる
makeAjaxRequest("google.com", "POST"); // methodがPOSTになる

ES6

// makeAjaxRequest の第2引数で指定するとif文が不要になる
function makeAjaxRequest(url, method = "GET") {
  // ajaxリクエストをするロジックがここにあると想定
  // ...
  return method;
}

makeAjaxRequest("google.com"); // methodがGETになる
makeAjaxRequest("google.com", "POST"); // methodがPOSTになる

Rest と Spread 演算子

スプレッド構文 - JavaScript | MDN

引数の部分に Rest 演算子を用いると可変長でまとめて配列に処理する

function addNumbers(a, b, c, d, e) {
  const numbers = [a, b, c, d, e];
  return numbers.reduce((sum, number) => {
    return sum + number;
  }, 0);
}

addNumbers(1, 2, 3, 4, 5);

渡す引数(a,b,c,d,e)を可変長にしたい場合 Rest 演算子を使う

function addNumbers(...numbers) {
  return numbers.reduce((sum, number) => {
    return sum + number;
  }, 0);
}

addNumbers(1, 2, 3, 4, 5, 6, 7);

Spread 演算子 = 展開する、広げる、フラットする = まとまっているものを分解する演算子(Rest とは逆)

const defaultMembers = ["Taro", "Hanako"];
const addedMembers = ["Ichiro", "Tomoko"];
const favoriteMembers = ["Jiro", "Sachiko"];
// これらをひとまとまりにしたい
// ES5
defaultMembers.concat(addedMembers); // ["Taro","Hanako","Ichiro","Tomoko"]

// Spread演算子を使う(配列の中身を展開してくれる)concatと同じ結果に
[...defaultMembers, ...addedMembers]; // ["Taro","Hanako","Ichiro","Tomoko"]

// favoriteMembers を先頭に持ってきたい
[...favoriteMembers, ...defaultMembers, ...addedMembers]; // ["Jiro","Sachiko","Taro","Hanako","Ichiro","Tomoko"]

// favoriteMembers の前に1つだけ'Saburo'を持ってきたい
// 間に'Kanako'を持ってきたい
["Saburo", ...favoriteMembers, "Kanako", ...defaultMembers, ...addedMembers]; // ["Saburo","Jiro","Sachiko","Kanako","Taro","Hanako","Ichiro","Tomoko"]
function validateNameList(...names) {
  // Rest演算子
  if (names.indexOf("Taro") < 0) {
    // もし'Taro'がなかったら、'Taro'を入れる
    return ["Taro", ...names]; // Spread演算子 ["Taro", "Hanako", "Ichiro"]
  }
  return names;
}

validateNameList("Hanako", "Ichiro");