2

newオペレーターを理解しようとしています。次の関数を見てください。

var _new = function(fn) {
    var obj = Object.create(fn.prototype);
    fn.apply(obj);
    obj.constructor = fn; // <--- EDIT: unnecessary
    return obj;
};

そのように適用できます:

var Test = function(){
    this.foo = 1;
};

var instance = _new(Test);

もちろん、任意の数の引数に簡単に拡張できます (単純にしようとしているだけです)。

newキーワードのように機能するようです。では、もしあれば違いは何ですか?newオブジェクトに対して他の演算子は何をしますか?

4

1 に答える 1

3

おっしゃる通り、これは基本的にnew行っていることです。継承する新しいオブジェクトを作成し、この新しいオブジェクトを参照してFunc.prototype呼び出します。Functhis

ただし、実装にはわずかな違いがあります。コンストラクター ( Func) がオブジェクトを返さないthis場合は、暗黙的に返されます。オブジェクト (任意のオブジェクト) を返す場合は、コンストラクター呼び出しの戻り値になります

したがって、より正確な複製は次のようになります。

var _new = function(fn) {
    var obj = Object.create(fn.prototype);
    var result = fn.apply(obj);
    return result != null && typeof result === 'object' ? result : obj;
};

それでおしまい。必要に応じて、条件演算子と同様に、構文糖衣として見ることができます。


リファレンスへのポインタ:newを使用すると、コンストラクタの内部[[Construct]]関数が呼び出されます。正確に何が起こるかは、仕様のセクション 13.2.2で説明されており、あなた (および私) が作成した関数とほとんど同じことを行います。

私が完全に確信していない点は、オブジェクトの内部[[Extensible]]プロパティが に設定されていることtrueです。作成するすべてのオブジェクトObject.createはデフォルトで拡張可能であると想定します(プロトタイプが拡張可能である場合)。

于 2013-04-02T16:48:51.290 に答える