プロパティと継承 JavaScriptの個人的なメモ (その5)

このメモについて

このメモは他の言語を習得している人用に向けて、それらとJavaScriptの違いを書いています。
誤りがあれば直しますので、ご指摘ください。

前回のメモ - プロトタイプ - JavaScriptの個人的なメモ (その4)

http://d.hatena.ne.jp/dhrname/20121101

プロパティの継承

プロパティは、インスタンス変数でもなければ、メンバでもありません。それらの代用はできます。見かけ上は同じです。
しかし、常に継承が働いているため、メソッドと同等です。このことを理解するために、次のコードを見てください。

var obj = {}; /*オブジェクトを作る*/

Object.prototype.x; /* undefined */
obj.x;              /* undefined */

Object.prototype.x = 12;
obj.x; /* 12 */

Object.prototype.x = 0;
obj.x; /* 0 */

オブジェクトobjのxプロパティの値は、常にObject.prototype.xと連動しています。これはプロトタイプチェーンをたどって、Object.prototypeまでさかのぼり、プロパティの値を参照しているからです。ただし、obj.xを直接、書き換えると、連動しなくなります。メソッドのオーバライドと同様です。

obj.x = 12;

Object.prototype.x = 25;
obj.x; /* 12 */

このように、プロパティには継承機能があって、代入がない限り、いつもプロトタイプを参照しようとします。ですから、プロパティには初期化が必要となります。

プロパティの初期化

プロパティの初期化には、オブジェクトリテラルや関数を使う方法があります。どの方法も、値を入れるだけです。
パフォーマンス上の理由から、以下の二つの方式が用いられることが多いです。

var obj = {
      x : 12
    },
    F = function() {
      this.x = 12;
    },
    ob = new F();

obj.x; /* 12 */
ob.x;  /* 12 */

親オブジェクトから継承する

プロトタイプを使って、親オブジェクトからプロパティを継承してみましょう。

/*コンストラクタ関数用のメソッド*/
Function.prototype.create = function(o) {
  this.prototype = o || {};
  return new this();
};
 var A = function() {
      this.n = 12;
    },
    B = function(){
      this.m = 1;
    },
    /*それぞれプロトタイプを設定してオブジェクトを作成*/
    a = A.create(),
    b = B.create(a),
    c = B.create(b);

a.n;  /* 12 を返す*/
b.n;  /* 12 を返す*/
c.n;  /* 12 を返す*/

結論

  • プロパティは親オブジェクトから継承します
  • 前もって設定しておかないと、Object.prototypeなど、コンストラクタ関数.prototypeの影響を受けます