LoginSignup
67
72

More than 5 years have passed since last update.

可読性アップのためのes2015入門

Last updated at Posted at 2016-01-11

さてjavascriptを書いている皆さん、 es2015への対応準備はいかがでしょうか?
個人的には 2016年こそがes2015元年になるのではないか(ややこしい)という見立てでおります。

無論、ブラウザ自体の対応はまだまだなのですが、
ブラウザ互換のjavascriptに変換してくれるBabelも(あるていど)安定し、
browserify等々との連携も便利になってきたこの頃、意識しなくても使えるようになってきたのでは、というこのごろです。

「そうは言っても、本来ブラウザで動かないし、javascriptに新しい機能が付くわけでもないし、使うメリットなんてそんなにないのでは?」
と思う方もいるかもしれません。自分もしばらくそう思ってました。

しかし明確なメリットが一つあります。
javascriptならではの読みづらい部分を、圧倒的に読みやすく書き直せることです。

そんなわけでこの記事では、javascriptの嫌なところを読みやすく書きなおすという観点のみで、es2015を紹介してみます。

class

こちらに何の変哲もないjavascriptがあります。押したらalertが出るだけのボタンを作るやつですね。

var HelloButton = function (name, btn) {
   this.name = name;
   this.btn = btn;

   this.setListener();
};

HelloButton.prototype.hello = function () {
    alert("hello, my name is " + this.name + " !");
};

HelloButton.prototype.setListener = function () {
    var that = this;
    this.btn.addEventListener('click', function (e) {
        that.hello();
    });
};

javascriptを書いている人なら、普通に「あ、クラスだ」と思うかもしれません。

しかしこれ厳密に言えば、これは「クラスっぽいもの」であってクラスではありませんし、別の書き方で「クラスっぽいもの」を実現している人もいます。(privateなプロパティはvar宣言にするなど)

また、これが「クラスっぽいな」と思うのは、prototypeの拡張が後からごろごろ書いてあるからであって、
例えば最初の5行くらいを見ただけでは、このHelloButtonという関数を、関数として使うのかクラスとして使うのかは判断しきれません。

それがes2015を使えばこのとおり、どう見たってクラスだね!というようなコードで書けます。

class HelloButton {
    constructor (name, btn) {
        this.name = name;
        this.btn = btn;

        this.setListener();
    }

    hello () {
        alert("hello, my name is " + this.name + " !");
    }

    setListener () {
        var that = this;
        this.btn.addEventListener('click', function (e) {
            that.hello();
        });
    }
}

coffeescript等を書いている人にとっては、とっつきやすい記法ではないでしょうか。extends等も同じような感じでできます。

ちなみにこちら、新しいリテラル(書き方)が提供されたというだけで、内部実装は前者と後者ほぼ変わらないということに注意です。
新しくクラスの概念ができたというよりは、みんながよく使う実装に正式な書き方ができた、という流れなのです。

arrow function

さて上記の例の中には他にも、javascriptを書く時に気持ち悪いと思うポイントが含まれています。例えばこちら、setListenerの中身を取り出したものです。

var that = this;
this.btn.addEventListener('click', function (e) {
    that.hello();
});

そのthatはなんなんだと。

念のため解説しておくと、こちらをthatなしで、そのままthis.hello()と書くとエラーになります。
var that = thisの行の時点では、thisには自分自身・つまりHelloButtonのインスタンスが入っていますが、
addEventListenerに渡されたfunctionの中・that.hello()の部分では、thisにはボタンの要素が入っています。
当然ボタンの要素はhelloメソッドを持っていないので、this.hello()で呼び出すとエラーになります。それを避けるため、HelloButtonのインスタンスがとれるタイミングで一度変数に代入しておき、後から参照する、という書き方がよく用いられているわけです。

この厄介な都合を避ける書き方も、es2015では提供されています。「arrow function」というやつです。

this.btn.addEventListener('click', (e) => {
    this.hello();
});

function (e) { ... }ではなく、(e) => { ... }という書き方にすることで、関数内部のthisは、その外側のthisを引き継ぐようになります。これで分かりやすいですね。
クラスを使った実装をする場面では少なくとも、このようにthisの内容がころころ変わらないように意識したほうが、読みやすいコードになると思います。

template

また、この辺も書く時にイライラする部分です。

alert("hello, my name is " + this.name + " !");

変数が入り混じった文字列を作りたい時の書き方ですね。これくらいなら変数が一つなのでなんとかなりますが、3つや4つと増えてきた時には見づらくてかなわないですね。

そこでes2015の「template」記法が使えます。

alert(`hello, my name is ${this.name} !`);

1, クオートを`に置き換える
2, 変数を入れ込みたい部分を${ ... }で囲む

とすることで、文字列全体を一組の``でまとめつつ、展開が必要なところだけ整理して書くことができます。ちなみに改行もOKです。

つまり

すべてを反映すると、最初のコードはこんな感じになります。

class HelloButton {
    constructor (name, btn) {
        this.name = name;
        this.btn = btn;

        this.setListener();
    }

    hello () {
        alert(`hello, my name is ${this.name} !`);
    }

    setListener () {
        this.btn.addEventListener('click', (e) => {
            this.hello();
        });
    }
}

色んな面で見やすくなったのではないでしょうか。
これなら、例えばRubyしか書いたことがない人でも、なんとなく読み取ってくれそうな気配さえします。

また結果的に、function文を使う場面がなくなっていることにも注目です。

環境構築

さて、みなさんes2015が書きたくなってきましたよね。
現状そのために必要な環境構築は、以下の様な感じです。

nodeをご利用のみなさま

→今すぐ書き換えちゃいましょう。

  • 一部use strictが必須です。
  • es2015をサポートし始めたのが4.0.0あたりからなので、package.jsonでenginesを4.0.0以上にするのをおすすめしてます。

フロントエンジニアのみなさま

→babel環境をととのえましょう。

ではではみなさま、今年も読みやすいjavascriptを書いていきましょうー!

67
72
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
67
72