0

このSOの質問は私を悩ませ続けました。これは、SOで定期的に再現されるように思われる質問です。

これで、プライベート'プロパティ'を管理しようとするコンストラクター関数を作成する方法を考案しました。これは、プライベートストレージを使用して、コンストラクターのプロトタイプget/setメソッドからのみ設定できます。基本的な形式では、次のようになります。

基本的なコンストラクター関数:

function Human(){
   /** set up a property storage **/   
   var storage = {
      name: { val: name || '-', get:true, set:true }
      ,age: { val: (age || '0'), get:true, set:true }
   };
   function get(){
       if (get.caller !== Human.prototype.get &&
           get.caller !== Human.prototype.set ){ return null }
       return storage;
   }
   this._get = get;
}

get/setプロトタイプメソッドをに追加するHuman

Human.prototype = {
     get: function(prop){
        return this._get()[prop];
     }
    ,set: function(prop, val){
       var storage = this._get();
       /** 
              set functionallity, returning 
              the current object after setting
              see jsfiddle link @ the bottom of
              this question
        **/
       return this;
    }
};
// usage
var pete = new Human('Pete',23);
pete.get('name'); //=> 'Pete'
pete.set('name','Pete Justin');
pete.get('name'); => 'Pete Justin'
// but
pete.name; //=> 'undefined'

私はあなたのコメントに本当に興味があります。多分私は完全に間違った方向に考えています、多分あなたはそれが不必要な操作であり、jsのプロトタイプの性質に違反していると言うかもしれません、それはすでに他の場所で(そしてより良い)行われています、または何か。教えてください!

私がこれについて考える-ここではそれを呼びましょう-パターン:それを使用して失うのは、プロパティ(など)を簡単に宣言して取得することの容易さですthis.some = that、あなたが勝つものは、より良いカプセル化、インスタンス変数のプライバシー、およびプロパティのいくつかの制御ですあなたが使用します(それが正しい用語であるかどうかはわかりませんが、OOPの世界では、誰もが用語に独自のプライベートな意味を与えているように見えることがあります)。

とにかく、私はこのjsfiddleHumanでより完全で動作するように調理しました。

4

1 に答える 1

2

まず第一に、この過度に設計されたソリューションは何を解決しようとしているのでしょうか?

プロトタイプからコンストラクターのローカル変数にアクセスしようとする問題は問題ではありません。プロトタイプを使用してすべてのデータを保存するだけでthis速度がわずかに向上するか、オブジェクトごとに追加の関数を作成することに文句を言わない (最小限のオーバーヘッド)。オブジェクトごとに追加の関数を作成するとコストがかかるというのはよくある誤解です。


問題はありませんが、コードは過度に設計されており、複雑であり、読んだり維持したりするのは当然のことのようです。この方法には利点がありませんか?this._store特権機能を作ってみませんか。

また、コンストラクターにローカル関数があるということは、すべてのオブジェクトに対して 1 つの関数を持つというプロトタイプの利点が失われることを意味します。また、プライベート変数を「エミュレート」するために、これに似たソリューションを過剰に設計しました。コードは、作業するのに適切な混乱になり、放棄する必要がありました。


コードの批判について:

.caller非標準です。使えません。ハックです。

this._store = {get:get};

だけではないのはなぜthis._store = getですか?

これ

function thisget(prop){
    return storage[prop];
}
return thisget(prop);

にインライン化する必要があります

return storage[prop]

于 2011-05-15T20:43:28.477 に答える