Yes, JavaScript Classes are Real Classes

Scotty Jamison
JavaScript in Plain English
5 min readSep 14, 2021

--

Have you heard arguments like this floating around?

There is no such thing as a “class” in JavaScript, nor does JavaScript support classical inheritance. JavaScript is forced to deviate in a variety of ways from the modern OOP concept of classes (meaning Java classes), due to the fact that its class syntax is built on top of prototypal inheritance. This can lead to odd and confusing behaviors for newcomers and seasoned developers alike. It’s better to simply not use the class syntax and embrace the prototypal nature of JavaScript.

Variations of this sort of impenetrable-sounding argument get passed around quite frequently, but with just a bit of digging, you’ll soon find that that this argument does not hold any weight. So let's grab a spade and get to work!

Are JavaScript classes full of oddities?

Original argument: “JavaScript is forced to deviate in a variety of ways from the modern OOP concept of classes (meaning Java classes), due to the fact that its class syntax is built on top of prototypal inheritance. This can lead to odd and confusing behaviors for newcomers and seasoned developers alike.”

Actually, most of these deviations have nothing to do with prototypal inheritance and have everything to do with the dynamic nature of JavaScript. The Python language makes for a pretty good validity-detection-tool against these types of “odd class behavior” arguments — if a particular argument against JavaScript classes also holds true for python classes, then that argument must not hold much weight, otherwise, we would have people in the python community running around with pitchforks and picket signs exclaiming “Death to python classes!”. So, let's line up some commonly cited arguments and see how they measure up against our validity-detection-tool.

Note: I intend for this section to be a “living” section. I’ll continue to update it to address future concerns people may bring up.

An instance can change classes at runtime

In JavaScript, it’s possible to switch your prototype at running by using Object.setPrototypeOf(). The same can be done in Python by modifying the __class__ field. If it’s not a problem in Python, it can’t be the “true problem” in JavaScript.

class Square:
width = 1
height = 1
class Circle:
r = 1
my_square = Square()
my_square.__class__ = Circle
print(isinstance(my_square, Square)) # False
print(isinstance(my_square, Circle)) # True
print(my_square.r) # 1

A class’s methods can be dynamically altered after the class has been declared

Python is a very dynamic language, so it also supports this kind of behavior as well.

class Square:
width = 1
height = 1
def area():
return width * height
my_square = Square()
Square.area = lambda self: 5
print(my_square.area()) # 5

You can instantiate a JavaScript class and receive a completely unrelated instance

This is talking about the fact that a JavaScript constructor function is able to return a value that’s not an instance of the constructed class.

class Square {
constructor() {
return { x: 2 }
}
}
const mySquare = new Square()
console.log(mySquare) // { x: 2 }
console.log(mySquare instanceof Square) // false

This can be done in Python as well.

class Square:
def __new__(*args):
return {'x': 2}
my_square = Square()
print(my_square) # {'x': 2}
print(isinstance(my_square, Square)) # False

Does JavaScript have classes and classical inheritance?

Original argument:There is no such thing as a “class” in JavaScript, nor does JavaScript support classical inheritance.”

While it is true that the class syntax is mostly syntax sugar for prototypes, this does not in-and-of-itself create a compelling reason to state that JavaScript does not have classes. After all, isn’t C++ in its entirety just syntax sugar for assembly/binary? It could be argued that C++ does not have real functions, because it’s just sugar for labels and gotos — you can even do some fancy memory tricks at runtime to pull back the curtains and reveal the truth of how functions operate, because, well, it’s C++ and it’ll let you do anything. It could also be said that Python classes aren’t real, they’re just syntax sugar for the built-in type() function (though no one says that). Anything you can do with Python’s class syntax can also be done dynamically with the type function, and yet, we say Python has classes.

So does JavaScript have classes? Does JavaScript support classical inheritance? The answer is an absolute yes! All it takes is a little sugar to give a language a feature.

Should JavaScript classes be avoided?

Original argument: “It’s better to simply not use the class syntax and embrace the prototypal nature of JavaScript.”

Whether or not you want to use the class syntax is up to you. There are valid reasons people may wish to avoid it. For example, you may find inheritance to already be a complicated enough topic, and having a language with two forms of inheritance (classical and prototypal) is just too much — it’s better to keep things simple and treat everything as prototypes. Or, maybe you don’t know why you dislike the class syntax, or why you like prototypes — it can be difficult to pinpoint the exact reasoning behind preferences. I wouldn’t be surprised if this “classes are odd because they are built on prototypal inheritance” theory keeps getting punted around precisely because people weren’t sure what it was they disliked about the class syntax, and that was an easy target to point fingers at.

If there’s anything I’ve learned, the best way to learn and develop your own opinion is to have conversations about these things, especially with those of opposing viewpoints, so feel free to start discussions in the comments (Just, please, be respectful).

Aside: I wouldn’t be surprised if I receive some comments talking about how the class syntax was simply added to make JavaScript a “grown-up” language, or because it wanted to look more OOP. I’m going to be pretty harsh against this theory upfront. This argument is a variation of a “the opposing group is just blindly following a dogma” argument. This is a very toxic line of thought that targets a specific group of people with hurtful labels such as “they just follow the crowd”, or, “they don’t have a good reason for their belief”. It’s really the same as a child getting frustrated, yelling “you just don’t get it”, and walking away — that sort of behavior is never going to help anyone learn anything. If you don’t think the class syntax was a good addition, that’s fine, tell me why it’s not a good fit for JavaScript, give me real arguments with actual substance! Don’t just say the language designers didn’t know what they were doing — that’s not arguing against the feature itself, that’s arguing against the reasons behind the feature, and is a pretty useless, destructive argument (and a logical fallacy).

Further reading

  • An opposing viewpoint. Their conclusion is the exact opposite: “But does that mean JavaScript actually has classes? Plain and simple: No.”
  • A (somewhat outdated) StackOverflow question on “Does JavaScript have classes”.
  • A similar viewpoint to mine, that also compares Python classes to Javascript classes.
  • Douglas Crockford — “The better parts” talk where he disavows the JavaScript class syntax altogether.

More content at plainenglish.io

--

--

A JavaScript addict since age 15. I love exploring topics such as language design and clean code, and I enjoy engaging in discussions around these principles.