1

次のコードがあるとしましょう。これは変更できません

var namespace = {};

function() {
    var MyConstructorFunction = function() {
        alert("default behavior");
    };

    namespace.MyConstructorFunction = MyConstructorFunction;

    setTimeout(function() {
        var instance = new MyConstructorFunction();
    }, 1000)
}();

で構築するnamespaceためにのみアクセスできるグローバルスコープにコードを外部から追加したいと思います。instancealert("custom behavior")

私の意図を明確にするために、次の 2 つのアプローチを考えることができるとしましょう。

namespace.MyConstructorFunction = function() {
    alert("custom behavior");
};

また

namespace.MyConstructorFunction.prototype.constructor = function() {
    alert("custom behavior");
};

しかし、明らかにそれらは機能しません。これを行う方法はありますか?

4

2 に答える 2

0

インスタンスの場合、コンストラクターをオーバーライドすることはできません。また、実際のアプリケーションでは、セキュリティ上の理由から、そうしたくありません。

ただし、特定のメソッドをオーバーライドまたは追加できます。

var F = function() {
  this.foo = 'bar';
}

var f = new F();
typeof f.foo; // "string"

f.foo = function() { return 'Bar' };
typeof f.foo; // "function"
于 2012-10-23T14:18:25.847 に答える
0

プロトタイプ チェーンを使用して、名前空間のメソッドをオーバーライドできます。

// create an object that inherits from namespace
var o = Object.create(namespace);

// Override the MyConstructorFunction property
o.MyConstructorFunction = function ()  {
    alert("custom behavior");
}

そして、名前空間トークンを再利用できます

namespace = o;

または、必要に応じて別の名前空間を使用することもできます。

Object.create は ES3 で完全にエミュレートできない ES5 機能ですが、この使用例では基本的なpolyfillで動作するはずです。


しかし、setTimeout とは別のコンストラクターを呼び出したいと考えていることは理解していますが、この例では不可能です。関数は、変更できないローカル変数を参照しています。この例のようにオブジェクトのグローバルな動作を変更することはできますが、それらの変数を参照できる関数を使用しない限り、クロージャ内の変数を変更することはできません。関数がローカル スコープの変数ではなく、グローバル スコープの変数を参照する場合は、運がいいでしょう。

すなわち:

var namespace = {};

function() {
    var MyConstructorFunction = function() {
        alert("default behavior");
    };

    namespace.MyConstructorFunction = MyConstructorFunction;

    setTimeout(function() {
        var instance = new namespace.MyConstructorFunction(); // reference global
    }, 1000)
}();
于 2012-10-23T14:12:01.927 に答える