文字与原型对象表示法的数据结构

时间:2013-12-19 00:32:41

标签: javascript object

我正在构建一个文本冒险来学习javascript,我不确定在使用对象原型时如何定位对象。 例如,使用文字语法,我定义了位置对象:

locations = {
    yard : {
        title: "Yard",
        description: "You are in the Yard. You can go east.",
        exits : {
            north : -1,
            east : "foyar",
            south : -1,
            west : -1
        },
        items: ["lamp"],
        points: 5
    },
        // etc..
}

并且可以找到这样的信息(例如):

currentLocation = locations[currentLocation]["exits"][direction]

...但是当我从原型中定义对象时,我不确定如何排列和定位对象:

function item(){
    this.id = undefined;
    this.title = "";
    this.description = "";
    this.points = 0;
    this.canTake = false;
}

var glasses = new item();
glasses.id = 1;
glasses.title = "Glasses";
glasses.description = "A scratched up pair of glasses. They aren't your prescription";
glasses.points = 10;
glasses.canTake = true;

在这里构建和引用我的数据的最佳方法是什么? (在这种情况下使用文字或原型方法是否有特别的优势?)

1 个答案:

答案 0 :(得分:0)

如果您有多个相同类型的对象实例(如项目似乎)并且它们有行为,那么您将把行为放在原型上。这是因为它在实例之间共享,在创建/存储它们时会节省你的CPU和内存。它还允许您通过使用继承来重新使用类似的项目逻辑(Employee是一个Person,因此名称,年龄和性别可以由Person初始化并由Employee重新使用,无需复制并粘贴代码)

例如:如果您的商品具有useIt功能,则匹配将与打火机的行为不同,因为匹配可以短时间使用一次,而打火机可以多次使用并且持续时间较长(直到它变得太热并爆炸)。

有关如何创建实例和使用原型的更多信息,请访问in this answer

以下是一些示例代码,您可以如何创建位置和项目:

//constructor for Item
var Item=function(args){
  //set canuse default to true or whats
  //  passed in args
  this.canUse=(typeof args.canUse==="undefined")?
    true:args.canUse;
  //cannot create an Item without description
  //  description doesn't have a default value
  if(typeof args.description==="undefined")
    throw new Error("Cannot create an item without description");
  this.description = args.description;
  //default value for usedTimes is 0 but can be an old
  // lighter that's been hused hundreds of times
  this.usedTimes=(typeof args.usedTimes==="undefined")?
    0:args.usedTimes;
};
//behavior on the prototype
Item.prototype.useIt=function(){
  this.usedTimes++;
};

//specify a match (should add jsdoc here so you know what args can be passed)
var Match=function(args){
  //re use Item code
  Item.call(this,args);
  //how powerfull is the Match (defaults to 5)
  this.burnPower=(typeof args.burnPower==="undefined")?
    5:args.burnPower
};
//Match behavior
Match.prototype.useIt=function(args){
  if(this.usedTimes!==0){
    //tell user it's used up
    return;
  }
 if(args.strikeOn && args.strikeOn.strikableSurface!==true){
    //tell user to to define a surfice to strike the match on
    return;
  }
  if(!args.useOn){
    //tell user to use it on ...
  }
  if(args.useOn.toBurn<=this.burnPower){
    //burn it and call Item to indicate it's used
    Item.prototype.useIt.call(this);
  }
};

//constructor for location
var Location = function(args){
  this.type=args.type;
  if(typeof this.type==="undefined")
    throw new Error("Cannot create a location without specifying type");
  this.title=(typeof args.title==="undefined")?
    args.type:args.title;
  //other stuff where type is mandatory
  this.items=[];
}
Location.prototype.addItem=function(item){
  this.items.push(item);
};
var args={},locations = {};

var loc=new Location({type:"Yard"});
loc.addItem(new Match({description:"A small match"}));
locations[loc.type]=loc;
console.log(locations);