2

私は node.js にかなり慣れていませんが、おそらく JavaScript も同様です。私は学ぶためにここにいます。

これが私がやろうとしていることです:

  • 「John」オブジェクトは、関数を含む「Client」オブジェクトからすべてを継承する必要があります
  • 新しいオブジェクトと継承をインスタンス化する際に、「new」キーワードの代わりに Object.create() を使用します

機能した単一ファイルのテストを次に示します。

var sys=require('sys');
var Client = {
  ip: null,
  stream : null,
  state: "Connecting",
  eyes: 2,
  legs: 4,
  name: null,
  toString: function () {
      return this.name + " with " +
      this.eyes + " eyes and " +
      this.legs + " legs, " + this.state + ".";
  }
}
var john = Object.create(Client, {
  name: {value: "John", writable: true},
  state :  {value: "Sleeping", writable: true}
}); 
sys.puts(john); // John with 2 eyes and 4 legs, Sleeping

これを複数のファイルに分割すると、次のようになります。

---- client.js ----

module.exports = function (instream, inip){
    return  {
         ip: inip,
          stream : instream,
          state: "Connecting",
          eyes: 2,
          legs: 4,
          name: null,
          toString: function () {
            return this.name + " with " +
              this.eyes + " eyes and " +
              this.legs + " legs, " + this.state + ".";
          },
    };

}; 

---- ジョン.js ----

var Client = require("./client");
module.exports = function (inname, instate){
    return Object.create(Client, {
      state : {value: inname, enumerable: false, writable: true},
      name: {value: instate, enumerable: true, writable: true},
    });

};

---- main.js ----

var sys = require("util");
var Client = require("./client")("stream","168.192.0.1");
sys.puts(Client); // null with 2 eyes and 4 legs, Connecting

var john = require("./john")("John","Sleeping");
sys.puts(john); //Function.prototype.toString no generic 
sys.puts(sys.inspect(john)); // { name: 'Sleeping' }
sys.puts(sys.inspect(john, true)); // {name: 'Sleeping', [state]: 'John'}

質問:

  1. ファイルを分割したり、問題を引き起こしている require() を使用したりする際に、何が間違っているのでしょうか?
  2. john オブジェクトの名前が「Sleeping」で状態が「John」なのはなぜですか? 行を配置した順序であることはわかっていますが、コンストラクターに配置したパラメーターに従うべきではありませんか?
  3. これを行うより良い方法はありますか?「new」キーワードに頼るのではなく、Object.create() を学ぶ傾向があります。
4

1 に答える 1

2

#2について:

return Object.create(Client, {
  state : {value: inname, enumerable: false, writable: true},
  name: {value: instate, enumerable: true, writable: true},
});

innameこれは、と を交換する単純なタイプミスinstateです。

#1について:

元の単一ファイル コードと新しい 3 ファイル コードの別のわずかな違いに問題があるのではないかと思います。特定のコメントがの MDN のページでObject.create私の目に留まりました。具体的には、

もちろん、Constructor 関数に実際の初期化コードがある場合、Object.create はそれを反映できません。

あなたのclient.jsファイルはコンストラクター関数を生成しています。あなたが書くつもりだったのjohn.jsは(#1と#2を組み合わせたものです):

return Object.create(Client(), {
  state : {value: instate, enumerable: false, writable: true},
  name: {value: inname, enumerable: true, writable: true},
});

関数ではなくオブジェクトを返すように Client 関数を呼び出し、その上に構築された新しいオブジェクトを作成します。

#3について:

このパターンを使用できなかった理由はわかりませんが、次のことを実証しました。

  1. 今日のほとんどの Javascript オブジェクトの作成方法とは異なります (ただし、より高速な構築メカニズムであることは間違いありません)。
  2. new古い Java スタイルの構文のように構文エラーが「飛び出さない」ように、新しい構文 ( を削除) を使用します。

それを覚えておいてください。でも、あなたがこの質問をしてくれたことをうれしく思いますObject.create。:)

于 2012-06-05T19:33:16.090 に答える