Borislav Hadzhiev
Fri Mar 11 2022·2 min read
Photo by Cristina Gottardi
Use the instanceof
operator to check if an object is an instance of a class,
e.g. if (myObj instanceof MyClass) {}
. The instanceof
operator checks if the
prototype
property of the constructor appears in the prototype chain of the
object and returns true
if it does.
class Person {} const p1 = new Person(); if (p1 instanceof Person) { console.log('✅ is instance of Person'); } else { console.log('⛔️ is not instance of Person'); } class Animal {} console.log(p1 instanceof Animal); // 👉️ false
The instanceof operator returns a boolean value indicating whether the prototype property of the constructor appears in the prototype chain of the object.
The p1
object was created using the Person
class, so it is an instance of
the class.
The instanceof
operator is very useful in TypeScript because it can be used as
a
type guard.
class Person { walk() { console.log('person is walking'); } } class Animal { run() { console.log('animal is running'); } } function example(x: Person | Animal) { // 👉️ x is type Person or Animal here if (x instanceof Person) { // 👇️ x is type Person here x.walk(); } else { // 👇️ x is type Animal here x.run(); } }
The function takes a parameter of type Person
or Animal
, so before we access
a class-specific method, we have to check an instance of which class was passed
to the function.
If you access the constructor.name
property, you can see that the class name
of the p1
object is Person
.
class Person {} const p1 = new Person(); console.log(p1.constructor.name); // 👉️ Person
We accessed the name
property on the
Object.constructor
property.
The Object.constructor
property returns a reference to the constructor
function, from which the object was created.
The instanceof
operator checks for the presence of constructor.prototype
in
the object's prototype chain.
class Person {} const p1 = new Person(); // 👇️ true console.log(Object.getPrototypeOf(p1) === Person.prototype);
Note that checking if an object is not an instance of a class is a bit tricky.
class Person {} class Animal {} const person = new Person(); if (!(person instanceof Animal)) { console.log('person is NOT an instance of Animal'); }
Notice that we used parenthesis around the instanceof check before negating it.
A commonly seen mistake is to omit the parenthesis, e.g.:
class Person {} class Animal {} const person = new Person(); // 👇️ Don't do this // ⛔️ Error: The left-hand side of an 'instanceof' // expression must be of type 'any', an object type // or a type parameter.ts(2358) if (!person instanceof Animal) { console.log('person is NOT an instance of Animal'); }
This code example inverts the value of the object and converts it to boolean, so
it becomes false
. We then check if false
is an instance of the Animal
class.
Wrapping the expression in parenthesis allows us to evaluate it as a whole.
If you don't like the parenthesis approach you can explicitly check if the
instanceof
operator returns false
.
class Person {} class Animal {} const person = new Person(); if (person instanceof Animal === false) { console.log('person is NOT an instance of Animal'); }
This achieves the same goal as using the logical NOT (!) operator with parenthesis, but is a little easier to read.