0

このコードを見てください:

        var Test = {
        options: {
            name: 'foo'
        },
        name: 'foo',
        init: function (name) {
            this.name = name;
            this.options.name = name;
        }
    };

    var dict = {};

    for (var i = 0; i < 3; i++) {
        var obj = Object.create(Test);
        obj.init(i);
        dict[i] = obj;
    }

オブジェクトdictのdict[X].options.nameのすべてのプロパティの値が同じvalue(2)で、dict [X] .nameのプロパティの値が異なる理由がわかりませんか?

4

3 に答える 3

1

参照による値の受け渡しと関係があるように見えます。

オブジェクトTestには、プロパティ内の別のオブジェクトへの参照が含まれていますoptions。の新しいインスタンスが作成されると、オブジェクトの新しいコピーを取得する代わりに、Test新しいインスタンスは既存のインスタンスへの参照を取得します。options

大まかな画像は次のようになります ここに画像の説明を入力してください

コードの下部に次のステートメントを追加することで確認できます

alert(Test.options== dict[0].options);
于 2011-09-14T12:21:51.953 に答える
1

ドキュメントは明確です:

指定されたプロトタイプオブジェクトとプロパティを使用して新しいオブジェクトを作成します。

新しいオブジェクトのプロトタイプもそうTestなります。すべてのインスタンスは同じプロトタイプを参照し、オブジェクトと同様に、このプロトタイプへの参照も共有します。options

関係は次のようになります。

+------------+      +---------+       +--------+
| Instance 1 |----->| Test    |       | Object |
+------------+      |         |       |        |
                    | options-|------>| name   | 
                    | name    |       +--------+
                    +---------+
                         ^ 
+------------+           |
| Instance 2 |-----------+
+------------+      

さて、optionsオブジェクトと同様に、それに新しいプロパティを割り当てると、次のようになります。

instance1.object.name2 = 'bar';

実際にアクセスして Test.optionsいます。結果は次のようになります。

+------------+      +---------+       +--------+
| Instance 1 |----->| Test    |       | Object |
+------------+      |         |       |        |
                    | options-|------>| name   | 
                    | name    |       | name2  |
                    +---------+       +--------+
                         ^
+------------+           |
| Instance 2 |-----------+
+------------+ 

ただし、に新しい値を割り当てると、そのインスタンスでname新しいプロパティnameが作成されます。だからあなたがするとき:

instance1.name = 'bar';

結果は次のようになります

+------------+      +---------+       +--------+
| Instance 1 |----->| Test    |       | Object |
|            |      |         |       |        |
| name       |      | options-+------>| name   | 
+------------+      | name    |       +--------+
                    +---------+
                         ^
+------------+           |
| Instance 2 |-----------+
+------------+      

optionsのプロパティにアクセスしたり、プロパティを割り当てたりする代わりに、新しい値を割り当てた場合も同じことが起こります。

instance1.options = {name: 'another name'};

結果:

           +--------+
           | Object |
           |        |
           | name   |
           +--------+
                ^
+------------+  |   +---------+       +--------+
| Instance 1 |--+-->| Test    |       | Object |
|            |  |   |         |       |        |
| options----+--+   | options-|------>| name   | 
+------------+      | name    |       +--------+
                    +---------+
                         ^
+------------+           |
| Instance 2 |-----------+
+------------+

プロパティルックアップがどのように機能するかにより、プロトタイプチェーンでinstance1.options最も近い(最も近い)プロパティの値を返します。またはインスタンスでoptions設定すると、プロトタイプ()の値ではなく、それらの値が返されます。nameoptionsTest

于 2011-09-14T12:26:07.597 に答える
0

ここで少し混乱していると思います。

options: {
    name: 'foo'
},
name: 'foo'

それらを定義し、Object.create()ステートメントで使用すると、プロトタイプに属し、同じプロトタイプを持つすべてのオブジェクトで同じになります。

属性が変更されたことがわかる理由nameは、次の呼び出しによって各インスタンスで属性を作成したためです(基本的にプロトタイプで定義されたものをオーバーライドします)。

this.name = name;

オブジェクトプロパティを直接割り当てたことがないため、オブジェクトプロパティでは発生しないことがあります。代わりに、最後に割り当てられた値(この例では2)を取ります。

あなたは書いていましたか:

this.options = {};
this.options.name = name;

関数内でinit--options.nameは各インスタンスでオーバーライドされ、希望どおりになります。

于 2011-09-14T12:33:21.340 に答える