Skip to content

Instantly share code, notes, and snippets.

@bvandgrift
Last active February 23, 2022 16:43
Show Gist options
  • Save bvandgrift/f9237587da5fe76ff50753db83c7d324 to your computer and use it in GitHub Desktop.
Save bvandgrift/f9237587da5fe76ff50753db83c7d324 to your computer and use it in GitHub Desktop.
simple decision logic demo for a friend's son currently javascripting
// more javascripty!
const FRIENDLY = {
MAYBE: 'pet at your own risk',
YES: 'ok to pet',
NO: 'do NOT pet'
}
class Pet {
constructor(name, isFriendly = FRIENDLY.MAYBE, sound = "UNKNOWN") {
this.name = name;
this.isFriendly = isFriendly;
this.sound = sound;
}
soundsLike() { return this.sound; }
canPet() { return this.isFriendly; }
}
class Dog extends Pet {
constructor(name) { super(name, FRIENDLY.YES, "woof!"); }
}
class Cat extends Pet {
constructor(name) { super(name, FRIENDLY.MAYBE, "meow!"); }
}
dog = new Dog("Spot");
cat = new Cat("Whisper");
what = new Pet("MysteryMeat");
// works but there are better ways
// deliberately ignoring the class functions here
const canPetIf = (pet) => {
let klass = pet.constructor.name;
console.log("---");
if (klass === 'Dog') {
console.log(`can you pet it? ${FRIENDLY.YES}.`);
} else if (klass === 'Cat') {
console.log(`can you pet it? ${FRIENDLY.MAYBE}.`);
} else if (klass === 'Pet') {
console.log(`can you pet it? ${FRIENDLY.MAYBE}.`);
} else if (pet instanceof Pet) {
console.log(`can you pet it? ${FRIENDLY.NO}.`);
} else {
// bounce if it's not a Pet
console.log(`${pet} doesn't look like a pet to me.`);
return;
}
console.log(`this critter is a ${klass} named ${pet.name}`);
console.log(`they make a '${pet.soundsLike()}' noise`);
};
console.log("\n### using `if/then/else`:");
canPetIf(dog);
canPetIf(cat);
canPetIf(what);
canPetIf('paintbrush');
// better, especially with many optionss
const canPetSwitch = (pet) => {
let klass = pet.constructor.name;
console.log("---");
switch(klass) {
case 'Dog': {
console.log(`can you pet it? ${FRIENDLY.YES}.`);
break;
}
case 'Cat': {
console.log(`can you pet it? ${FRIENDLY.MAYBE}.`);
break;
}
case 'Pet': {
console.log(`can you pet it? ${FRIENDLY.MAYBE}.`);
break;
}
default: {
// we can catch previously undefined types if we want
if (pet instanceof Pet) {
console.log(`can you pet it? ${FRIENDLY.NO}.`);
} else {
// bounce if it's not a Pet
console.log(`${pet} doesn't look like a pet to me.`);
return;
}
}
}
console.log(`this critter is a ${klass} named ${pet.name}`);
console.log(`they make a '${pet.soundsLike()}' noise`);
}
console.log("\n\n### using `switch`:");
canPetSwitch(dog);
canPetSwitch(cat);
canPetSwitch(what);
canPetSwitch("ham sandwich");
// using types and class functions, it doesn't matter when we define the new
// type. the function will still behave.
class VampireBat extends Pet {
constructor(name) { super(name, FRIENDLY.NO, "HIGH PITCH SQUEAKING"); }
}
bat = new VampireBat("Dracula");
canPetSwitch(bat);
// the best way in an OO language is to make all the things you
// care about accessible regardless of type. no decision logic at all.
const canPetOO = (pet) => {
console.log("---");
// guard clause:
if (!(pet instanceof Pet)) {
console.log(`${pet} doesn't look like a pet to me.`);
return; // you only get to use the Pet functions if it's a Pet instance
}
console.log(`this critter is a ${ pet.constructor.name } is named ${ pet.name }`);
console.log(`they make a '${pet.soundsLike()}' noise`);
console.log(`can you pet it? ${ pet.canPet() }.`);
}
console.log("\n\n### using type inheritance only:");
canPetOO(dog);
canPetOO(cat);
canPetOO(what);
canPetOO(bat);
canPetOO(Math.PI);
### using `if/then/else`:
---
can you pet it? ok to pet.
this critter is a Dog named Spot
they make a 'woof!' noise
---
can you pet it? pet at your own risk.
this critter is a Cat named Whisper
they make a 'meow!' noise
---
can you pet it? pet at your own risk.
this critter is a Pet named MysteryMeat
they make a 'UNKNOWN' noise
---
paintbrush doesn't look like a pet to me.
### using `switch`:
---
can you pet it? ok to pet.
this critter is a Dog named Spot
they make a 'woof!' noise
---
can you pet it? pet at your own risk.
this critter is a Cat named Whisper
they make a 'meow!' noise
---
can you pet it? pet at your own risk.
this critter is a Pet named MysteryMeat
they make a 'UNKNOWN' noise
---
ham sandwich doesn't look like a pet to me.
---
can you pet it? do NOT pet.
this critter is a VampireBat named Dracula
they make a 'HIGH PITCH SQUEAKING' noise
### using type inheritance only:
---
this critter is a Dog is named Spot
they make a 'woof!' noise
can you pet it? ok to pet.
---
this critter is a Cat is named Whisper
they make a 'meow!' noise
can you pet it? pet at your own risk.
---
this critter is a Pet is named MysteryMeat
they make a 'UNKNOWN' noise
can you pet it? pet at your own risk.
---
this critter is a VampireBat is named Dracula
they make a 'HIGH PITCH SQUEAKING' noise
can you pet it? do NOT pet.
---
3.141592653589793 doesn't look like a pet to me.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment