Object Composition alternatives

I'm Luke

@luke_dot_js

@lukewestby

@luke

Ways to compose objects

  • class / new
  • Object.create()
  • Object.assign()

Task:

  • Create Dog and Cat instances
  • Both animals have a name
  • Both animals can walk()
  • Dogs can bark()
  • Cats can knockStuffOffCounter()
class
class Animal {
  constructor(name) {
    this.name = name;
  }
  walk() {
    console.log(`${this.name} walked over there`);
  }
}

class Dog extends Animal {
  bark() {
    console.log(`${this.name} said "woof"`);
  }
}

class Cat extends Animal {
  knockStuffOffCounter() {
    console.log(`${this.name} knocked a full glass of water over`);
  }
}
Object.create()
const animalProto = {
  init(name) {
    this.name = name;
  },
  walk() {
    console.log(`${this.name} walked over there`);
  }
};

const dogProto = Object.create(animalProto);
Object.assign(dogProto, {
  bark() {
    console.log(`${this.name} said "woof"`);
  }
});

const catProto = Object.create(animalProto);
Object.assign(catProto, {
  knockStuffOffCounter() {
    console.log(`${this.name} knocked a full glass of water over`);
  }
});
Object.create() cont.
function createDog(name) {
  const instance = Object.create(dogProto);
  instance.init(name);
  return instance;
}

function createCat(name) {
  const instance = Object.create(catProto);
  instance.init(name);
  return instance;
}
animalProto
dogProto
createDog('[name]')

[[Prototype]]

[[Prototype]]

Object.assign()
const animal = {
  init(name) {
    this.name = name;
  },
  walk() {
    // ...
  }
};

const dog = {
  bark() {
    // ...
  }
};

const cat = {
  knockStuffOffCounter() {
    // ...
  }
};
Object.assign() cont.
function createDog(name) {
  const instance = Object.assign({}, dog, animal);
  instance.init(name);
  return instance;
}

function createCat(name) {
  const instance = Object.assign({}, cat, animal);
  instance.init(name);
  return instance;
}
Object.assign() alt.
const walker = {
  walk() {
    // ...
  }
};

const nameable = {
  init(name) {
    this.name = name;
  }
};

const barker = {
  bark() {
    // ...
  }
};

const messCreator = {
  knockStuffOffCounter() {
    // ...
  }
};
Object.assign() alt. cont.
function createDog(name) {
  const instance = Object.assign({}, nameable, walker, barker);
  instance.init(name);
  return instance;
}

function createCat(name) {
  const instance = Object.assign({}, nameable, walker, messCreator);
  instance.init(name);
  return instance;
}
function createPuppy(name) {
  const instance = Object.assign({},
    nameable, walker, barker, messCreator);
  instance.init(name);
  return instance;
}

Caveat Emptor

Instantiation is way faster than other methods

 

http://jsperf.com/object-create-vs-object-assign-vs-new/3

JavaScript object composition alternatives

By lukewestby

JavaScript object composition alternatives

  • 791