LoginSignup
69
66

More than 5 years have passed since last update.

JavaScriptでのクラス定義

Last updated at Posted at 2013-07-31

よく使うパターン

あんまり意味のないHelloクラスを定義してみる

var Hello = (function(){
    // constructor
    function Hello(name){
        this._name = name;
    }

    // private method
    function say(message){
        console.log(message + ', ' + this._name);
    }

    // public method
    function hello(){
        say.call(this, 'Hello');
    }

    Hello.prototype = {
        // constructor 修正
        constructor: Hello,
        // 以下 public メソッド
        hello: hello
    };
    return Hello;
}());

このパターンのポイントは、即時関数内にクラスに関係あるメソッドや変数をまとめるところ。
クラスの定義以外は、即時関数の外を汚さない。
また、公開したいインターフェースは最後のprototypeに列挙するだけでいいのもポイント高い。

継承

このパターンで継承する場合ちょっとややこしくなる。
というかJSで継承しようとするとややこしくなる。

var Animal = (function(){
    function Animal(name){
        this._name = name;
    }
    function say(){
        throw new Error('not implemented');
    }
    Animal.prototype = {
        constructor: Animal,
        say: say
    };
    return Animal;
}());

var Dog = (function(){
    function Dog(name){
        // super call
        Animal.call(this, name);
    }
    function say(){
        console.log('bowwow');
    }
    // Animal.prototype をプロトタイプチェーンに追加したいが、コンストラクタが邪魔なのでちょっと細工する
    Dog.prototype = (function(){
        function F(){}
        F.prototype = Animal.prototype;
        return new F();
    }());

    // 複数メソッドを定義する場合、並べて書かないとダメなのであまりイケてない
    Dog.prototype.constructor = Dog;
    Dog.prototype.say = say;
    return Dog;
}());

Object.create が使えるなら

ちょっとスマートに書ける

var Animal = (function(){
    function Animal(name){
        this._name = name;
    }
    function say(){
        throw new Error('not implemented');
    }
    Animal.prototype = {
        constructor: Animal,
        say: say
    };
    return Animal;
}());

var Dog = (function(){
    function Dog(name){
        // super call
        Animal.call(this, name);
    }
    function say(){
        console.log('bowwow');
    }
    // すっきり!
    Dog.prototype = Object.create(Array.prototype);

    // でもここはやっぱりイケてない
    Dog.prototype.constructor = Dog;
    Dog.prototype.say = say;
    return Dog;
}());
69
66
1

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
69
66