Повний посібник із прикладами

JavaScript – це універсальна мова програмування, що підтримує різноманітні підходи, включаючи функціональне, об’єктно-орієнтоване та імперативне програмування.

Для втілення об’єктно-орієнтованих принципів JavaScript використовує класи. Їх розуміння є ключовим, тому ця стаття слугує вичерпним керівництвом по класах JavaScript та їх застосуванню.

Що таке класи в JavaScript?

В об’єктно-орієнтованому підході системи моделюються як набори об’єктів, що взаємодіють між собою. Об’єкти зберігають інформацію у властивостях та виконують дії за допомогою методів. Клас визначає, які властивості та методи притаманні об’єктам певного типу. Таким чином, класи виступають як шаблони для створення об’єктів.

Основні терміни, що використовуються в класах

Щоб уникнути непорозумінь, розглянемо ключові терміни, що будуть використовуватись в цій статті. Якщо ви вже знайомі з об’єктно-орієнтованим програмуванням, можете перейти до наступного розділу.

❇️ Клас – це схема або шаблон для створення об’єктів. Створення об’єкта на основі шаблону класу називається інстанціюванням.

❇️ Член класу – це будь-який елемент, що належить класу. Існує два основних типи членів класу: методи та властивості.

❇️ Властивість – це член класу, що призначений для зберігання значень. Це можуть бути як прості типи даних, такі як числа та рядки, так і складні об’єкти та масиви.

❇️ Деякі властивості є доступними лише в межах класу – їх називають приватними. Інші властивості є доступними як в середині, так і за межами класу – їх називають публічними.

❇️ Метод – це функція, що визначена всередині класу. Вона належить класу і має доступ до його публічних і приватних властивостей. Подібно до властивостей, методи також можуть бути публічними або приватними.

❇️ Деякі методи слугують інтерфейсом для взаємодії зовнішнього коду з властивостями класу. До них належать гетери (getters), що отримують значення властивостей, і сетери (setters), що встановлюють значення властивостей.

❇️ Деякі члени класу є статичними. Це означає, що вони доступні безпосередньо через клас, а не через екземпляри (об’єкти) класу.

На противагу статичним, нестатичні члени класу доступні лише через екземпляри класу. Для доступу до нестатичного члена спочатку потрібно створити об’єкт класу.

Коли створюється екземпляр класу, викликається спеціальний метод, призначений для налаштування властивостей екземпляра. Цей метод називається конструктором.

Пояснення інстанціювання класу

Для створення екземпляра класу в JavaScript використовується ключове слово new разом з назвою класу. Наприклад, для створення екземпляра класу Array:

const myArr = new Array()

Створення класів в JavaScript

У цьому розділі розглянемо створення класу, що реалізує всі концепції, описані у розділі «Основні терміни, що використовуються в класах». Ми зробимо це на прикладах, де кожен наступний приклад базується на попередньому.

Оголошення порожнього класу

Для оголошення класу в JavaScript використовується ключове слово class, за яким слідує назва класу. Далі йде тіло класу, обмежене фігурними дужками, що містить усі члени класу.

Приклад оголошення класу з порожнім тілом:

class Dog {

}

Тепер можна створити екземпляр класу та вивести його в консоль.

const pet = new Dog;
console.log(pet);

Створення публічних властивостей

Публічні властивості визначаються за допомогою ідентифікатора та необов’язкового значення.

class Dog {
    name = "Roy";
    age;
}

Тут ми визначили властивість name зі значенням рядка та властивість age без початкового значення.

const pet = new Dog();

console.log(pet.name);
console.log(pet.age);

Визначення публічних методів

Методи додаються до класу всередині його тіла. Метод визначається подібно до функції, але без ключового слова function.

class Dog {
    name = "Roy";
    age;

    walk () {
        console.log("Walking");
    }
}

У прикладі вище ми визначили метод walk. Кожен екземпляр класу Dog матиме цей метод.

const pet = new Dog();
pet.walk();

Доступ до властивостей з методів

Зазвичай доступ до властивостей об’єкта здійснюється за допомогою оператора крапки. Наприклад, щоб отримати доступ до властивості name об’єкта person, використовується вираз person.name.

Для доступу до властивості з методу об’єкта використовується ключове слово this замість назви об’єкта, наприклад: this.name. this вказує на поточний об’єкт. Для доступу до властивостей класу з його методів використовується синтаксис this.назва_властивості.

Створення приватних властивостей

Припустімо, що потрібно зробити властивості name та age приватними. У такому разі клас матиме вигляд:

class Dog {
    #name = "Roy";
    #age;

    walk () {
        console.log("Walking");
    }
}

Приватні властивості позначаються символом #. Спроба доступу до них ззовні призведе до помилки.

const dog = new Dog();

dog.#name

Створення методів Getter та Setter

Оскільки властивості name та age тепер приватні, доступ до них можливий лише через методи класу.

Для дозволу доступу ззовні, використовуються гетери та сетери. Наприклад, для властивості name:

class Dog {
    #name = "Roy";
    #age;

    get name () {
        return this.#name;
    }

    set name (value) {
        this.#name = value;
    }

    walk () {
        console.log("Walking");
    }
}

За допомогою вищеописаного класу, можна встановити та отримати значення імені за допомогою наступного коду:

const pet = new Dog();

// Встановлення імені
pet.name = "Rex";

// Отримання імені
console.log(pet.name);

Створення приватних методів

Подібно до приватних властивостей, приватні методи мають префікс #. Оголошення приватного методу має вигляд:

class Dog {
    #name = "Roy";
    #age;

    get name () {
        return this.#name;
    }

    set name (value) {
        this.#name = value;
    }

    #increaseAge() {
        this.#age ++;
    }

    #decreaseAge () {
        this.#age --;
    }

    walk () {
        console.log("Walking");
    }
}

Спроба виклику цих методів ззовні призведе до помилки.

const pet = new Dog();
pet.#increaseAge();

Створення методу-конструктора

Метод-конструктор викликається автоматично при створенні нового екземпляра класу. Він використовується для ініціалізації властивостей. У нашому прикладі ми ініціалізуємо властивості age та name з аргументами, переданими при створенні екземпляра:

class Dog {
    #name;
    #age;

    constructor (name = "Dog", age = 0) {
        this.#name = name;
        this.#age = age;
    }

    get name () {
        return this.#name;
    }

    set name (value) {
        this.#name = value;
    }

    #increaseAge() {
        this.#age ++;
    }

    #decreaseAge () {
        this.#age --;
    }

    walk () {
        console.log("Walking");
    }
}

Під час створення екземпляра класу, можна задати значення імені та віку:

const pet = new Dog('Roy', 3);
console.log(pet.name);

Створення статичних властивостей та методів

Статичні члени класу доступні без створення екземпляра класу. У прикладі нижче ми створимо статичну властивість та метод.

class Dog {
    #name;
    #age;
    static genus = "Canis";

    constructor (name = "Dog", age = 0) {
        this.#name = name;
        this.#age = age;
    }

    static bark() {
        console.log("Woof");
    }

    get name () {
        return this.#name;
    }

    set name (value) {
        this.#name = value;
    }

    #increaseAge() {
        this.#age ++;
    }

    #decreaseAge () {
        this.#age --;
    }

    walk () {
        console.log("Walking");
    }
}

Тепер можна отримати доступ до статичної властивості та методу без створення об’єкта:

console.log(Dog.genus);
Dog.bark();

Спадкування

Класи можуть успадковувати властивості від інших класів. Клас, який успадковує від іншого класу, називається підкласом або суперкласом, а клас, від якого він успадковує – базовим класом.

Для створення суперкласу в JavaScript використовується ключове слово extends. Наприклад, успадкуємо клас Dog:

class Rottweiler extends Dog {
    constructor (name, age) {
        super(name, age);
        this.breed = 'rottweiler';
    }
}

Клас майже не змінився. У конструкторі викликано функцію super(), яка посилається на конструктор базового класу. Тому ми викликали конструктор базового класу всередині нашого суперкласу, передавши ім’я та вік.

const myPet = new Rottweiler();
console.log(myPet);

Висновок

У цій статті ми розглянули класи, їх визначення, типи членів, що можуть входити до них, та їх класифікацію. Все це було проілюстровано прикладами.

Далі можна ознайомитись з питаннями для співбесіди з об’єктно-орієнтованого програмування.