JavaScript Lesson 30 – Composition in OOP

Tram Ho

After learning about Inheritence , Encapsulation , Polymorphism , Abstraction , and how to manifest in JavaScript code when referencing from Java ; There are a few features that I feel are essential to finding the right way to represent. That is:

First , the Encapsulation encapsulation feature borrows in part from the protected label, which limits access to elements that are only available in the legacy line. The solution referenced from JavaScript.info is heavily reliant on self-generated logic conventions. That is, technically, elements named with _ in front of them are still public and the coder will have to limit themselves to writing access to those elements.

Second , the ability to create a reference surface using an interface to a compatible object and hide all other elements unrelated to that interface . This in OOP is called a blackbox , when the code uses an object that doesn’t know the details of the object it is interacting with. The solution that I found earlier can only help to use interface as an abstraction design tool, to create constraints for the writing phase of code that implements detailed logic.

Hmm… surely there must be another way of expressing logic that works like this. The general idea is that an example in the Java environment, where the form of Multi-Inheritance is not supported at the syntactic level of the language, was reimagined by creating a code architecture. called Object Composition .

image.png

That is, instead of copying the elements present in the Trait into the class to use, people will attach each Trait to a property in that class . And when making access to an element in that Trait , the syntax will be object.trait.method() . A bit cumbersome, but the important thing is that the necessary feature has appeared.

So let’s try to do a few examples to see how Object Composition can improve what OOP tools in JavaScript do not yet technically support.

Protected State

Since JavaScript has no encapsulation logic at the directory level, so when borrowing the operation logic of the protected label from Java , what we want is: to be able to define non-open property like public , but also is not closed in the scope of that class like #private , but can be available in the scope of derived class .

So, first, so that the property are not open like public , we will define them all as #private .

However, now we also want class that inherit Person to also have direct access to these properties. That is, it is necessary to support the extends operation that can bring these properties from the class Person to the derived class .

If so, now we need these properties to be made public when we perform the inheritance operation. And this is only possible if we separate the properties into another class .

image.png

Here, I temporarily use the word Entity (entity) to name representative class , with additional method describing the ability to act, interact, and simulate human entities; The word Record is used to name the data class , describing a record in the database .

Considering the interface using class Entity , the #state are private , so it is possible to limit the accessibility from the code defined outside the inheritance line. As for the class Record , the name , age , etc. data fields are all public , so they can be inherited by other class Record .

So in case PersonRecord contains many state properties, we can be supported by extends operation and do not have to redefine when we need to create a class that inherits PersonEntity .

So we have #name available to the code defined inside the derived class and hidden from the code defined outside. The way to handle protected state for abstract class is completely similar, so we don’t need to add example code anymore.

Regarding the encapsulation of method method , it is not really necessary, because in fact, method that need to be hidden in private or protected form are all a kind of sub-program that supports method to open in public form. And so we can all turn into sub-program defined outside the class space, then from the main method will be able to pass in the necessary parameters the sub-program support.

Blackbox Referencing

First of all, let’s review this feature in Java that we already know through the example of the previous article. Let’s say we have a class Person that implements the Crafter and Teacher interfaces. An operation referencing the interface Crafter will not be able to use methods not declared in that interface .

This feature is implemented in Java because the identifier names are all well-typed and the compiler will be able to perform lookup logic to the definition of the interface in use. However, for a dynamic-typing language like JavaScript , we need to find a solution ourselves. Will still be Object Composition . And here is the reference through an interface in JavaScript :

That means each interface will need to be implemented with a corresponding trait and attached to a property of the class Entity that uses that trait .

Here is a little note in the example code of the trait , usually the trait will be defined with all the property needed to be used for the method method present in that trait . However, to clarify the logic of referencing the superstate , I did not define name and age in the trait Teacher.Record .

Where ascrafter = new Crafter.Trait() uses an empty new Object() instead for the symbol; Since we are just trying to refer to the teach() method which is not in the design of Crafter.Trait .

Oh.. and with this implementation, if we want a property in wukong.#state that can be opened for external code to use, we can create an additional trait named like asaccess that holds the parameter refer to #superstate .

The asaccess will then be able to externally provide the public and return #state.property open methods it wants to open. As such, we can still decide which property will be accessible at the public or protected level if desired.

summary

So with the class Entity design consisting of a single object #state and object trait that hold a reference to superstate = entity.#state . We were able to really borrow the operation logic of protected property and limit reference via the interface of a statically typed language like Java .

In addition to the related concepts introduced, OOP has another popular category called Design Patterns . If you have time to learn more about this topic, here I have a series of translations from Tutorialspoint.com: [Design Patterns] Một Số Dạng Thức Triển Khai Trong OOP .

And a Series that I follow, translated in detail from Refactoring.guru: Design Patterns - Ren

This is also the last article in this series of articles introducing OOP in this Sub-Series. And now we will move on to another programming paradigm called Event-Driven Programming .

(unpublished) [JavaScript] Lesson 31 – Event-Driven Programming

Share the news now

Source : Viblo