OOP:属于类和继承的计数器

时间:2011-09-20 14:17:43

标签: javascript oop inheritance

我有一个类的层次结构,我希望每个对象都有一个Classname-integer形式的ID(示例:Car-0Car-1Motorcycle-0Truck-0Truck-1,...)

类层次结构是

Vehicle
   Car
   Motorcycle
   Truck

问题是:我只想编写一次管理ID的代码,而我在构造函数,原型,后期绑定等方面都丢失了。

我想用伪代码获取的示例:

car = new Car
anotherCar = new Car
car.id                  // "Car-0"
anotherCar.id           // "Car-1"
truck = new Truck
truck.id                // "Truck-0"

Car构造函数使用当前的Car可用id初始化对象id,然后递增它以使下一个新Car具有不同的id。这不得影响其他类ID。

理想情况下,我想在基类Vehicle中编写代码,但我不知道是否可能。

我目前使用的目标语言是Coffeescript / Javascript,但欢迎使用其他语言,并提供有关其工作原理的一些推理。

你会如何解决这个问题?

4 个答案:

答案 0 :(得分:2)

您可以使用Vehicle构造函数添加将更新ID的原型函数,如下所示:http://jsfiddle.net/ZDUEk/

(function() {
    var ids = {}; // remember last id

    function Vehicle() {

    }

    Vehicle.prototype.applyVars = function() {
        var name = this.constructor.name, // Car or Truck
            id   = ids[name];

        if(!id) {
            id = ids[name] = 0; // init id
        }

        this.id = name + "-" + id; // set to form Type-X

        ids[name]++; // increment for next id
    };

    function Car() {
        this.applyVars(); // set id
    }

    function Truck() {
        this.applyVars(); // set id
    }

    Car.prototype = new Vehicle;
    Car.prototype.constructor = Car;

    Truck.prototype = new Vehicle;
    Truck.prototype.constructor = Truck;

    window.Vehicle = Vehicle;
    window.Car = Car;
    window.Truck = Truck;
})();

var car1   = new Car,
    car2   = new Car,
    truck1 = new Truck;

alert([car1.id, car2.id, truck1.id]);

答案 1 :(得分:1)

使用Object.createpd

// Vehicle prototype
var Vehicle = {
  drive: function() {
    // code
  },
  name: "Vehicle",
  counter: 0
}

// Car prototype
var Car = Object.create(Vehicle, pd({
  name: "Car",
  counter: 0
  // car methods
}));

// vehicle factory
var vehicle = function(data, proto) {
  proto = proto || Vehicle;
  data.id = proto.name + proto.counter++;
  return Object.create(proto, pd(data));
};

// car factory
var car = function(data) {
  return vehicle(data, Car);
};

这里你想要的是在原型上存储名称和计数器。然后你的车辆工厂只在原型计数器上生成一个新的ID。名。

答案 2 :(得分:0)

我从@ pimvdb的帖子中借鉴了一些想法并提出了这个Coffeescript片段:

class Vehicle
    @ids = {}
    @name = 'Vehicle'
    constructor: ->
        @constructor.ids[@constructor.name] ?= 0
        @type = @constructor.name
        @id = "#{@type}-#{@constructor.ids[@type]++}"

class Car extends Vehicle
    @name = 'Car'

class Truck extends Vehicle
    @name = 'Truck'

car = new Car
alert car.id
car = new Car
alert car.id
truck = new Truck
alert truck.id
car = new Car
alert car.id

可在此处测试:http://jashkenas.github.com/coffee-script/(点击“try coffeescript”)

看似我正在寻找的东西,谢谢。

答案 3 :(得分:-1)

将您的示例翻译成更正式的描述:一些构造者拥有自己的ID经销商。

// a Vehicle has an id property, but no id dealer
function Vehicle( id ){
   this.id=id;
}
Vehicle.prototype.id = function(){ return this.id; }

// some objects can deal IDs
function IDDealer(){
   this.nextid=0;
}
IDDealer.prototype.nextId = function(){
   this.nextid ++;
   return this.nextid;
}


function Car(){
   Vehicle(this, idDealer.nextId() );
}
// a Car has a proper ID dealer
Car.prototype.idDealer = new IDDealer();


function Truck(){
   Vehicle(this, idDealer.nextId() );
}
// a Truck has a proper ID dealer
Truck.prototype.idDealer = new IDDealer();