Объектке багытталган программалоодо класс бул объекттерди түзүү үчүн кеңейтилүүчү код шаблоны, аларда баштапкы маанилерди (касиеттер) жана ишке ашыруу жүрүм-турумдарын (ыкмаларын) орноткон.
Wikipedia
Иш жүзүндө, биз көп учурда бир эле түрдөгү көптөгөн объекттерди, мисалы, колдонуучуларды, продукттарды же башка нерсени түзүшүбүз керек.
Биз буга чейин Конструктор бөлүмүнөн белгилүү болгондой , "жаңы" оператор буга жардам бере алат new function
.
Бирок заманбап JavaScript объектиге багытталган программалоо үчүн пайдалуу жаңы функцияларды камсыз кылган бир кыйла өркүндөтүлгөн "класс" конструкциясына ээ.
Синтаксис "класс"
Негизги синтаксис төмөнкүдөй көрүнөт:
@A@class MyClass {
// методы класса
constructor() { ... }
method1() { ... }
method2() { ... }
method3() { ... }
...
}@A@
new MyClass()
Андан кийин бардык көрсөтүлгөн ыкмалар менен жаңы объект түзүү үчүн чакырууну колдонуңуз .
Бул учурда, ыкма автоматтык түрдө деп аталат constructor()
, анда биз объектти инициализациялай алабыз.
Мисалы:
@A@class User {
constructor(name) {
this.name = name;
}
sayHi() {
alert(this.name);
}
}
// Использование:
let user = new User("Иван");
user.sayHi();@A@
Чакырганда new User("Иван")
:
- Жаңы объект түзүлдү.
constructor
берилген аргумент менен иштейт жана аны сактайтthis.name
.
…Андан кийин объектте методдорду чакыра аласыз, мисалы user.sayHi()
.
Жаңыдан иштеп чыгуучулардын кеңири тараган катасы класстык методдордун ортосуна үтүр коюу болуп саналат, бул синтаксистик катага алып келет.
Класс синтаксиси объекттин литералдарынан айырмаланат, аларды чаташтырбаңыз. Класстарда үтүр коюу талап кылынбайт.
Класс деген эмне?
Анда бул эмне class
? Бул биринчи караганда сезилиши мүмкүн, толугу менен жаңы тил жак эмес.
Келгиле, сыйкырдын баарын жок кылып, класс деген эмне экенин көрөлү. Бул көптөгөн татаал аспектилерин түшүнүүгө жардам берет.
JavaScript-те класс бул функциянын бир түрү.
Карап көрүңүз:
@A@class User { constructor(name) { this.name = name; } sayHi() { alert(this.name); } } // доказательство: User - это функция alert(typeof User); // function@A@
Бул жерде курулуш иш жүзүндө эмне кылатclass User {...}
:
User
Класс жарыялоосунун натыйжасы катары аталган функцияны түзөт . Функциянын коду методдон алынатconstructor
(эгерде андай ыкма жок болсо бош калат).sayHi
, сыяктуу бардык ыкмаларды сактайтUser.prototype
.
Объект боюнча методду чакырганда, ал F.prototypenew User
бөлүмүндө сүрөттөлгөндөй прототиптен алынат . Ошентип, объекттер класстык методдорго мүмкүнчүлүк алышат.new User
Сүрөттө декларациянын жыйынтыгы көрсөтүлгөн class User
:
Жогорудагы кодду текшере аласыз:
@A@class User {
constructor(name) { this.name = name; }
sayHi() { alert(this.name); }
}
// класс - это функция
alert(typeof User); // function
// ...или, если точнее, это метод constructor
alert(User === User.prototype.constructor); // true
// Методы находятся в User.prototype, например:
alert(User.prototype.sayHi); // sayHi() { alert(this.name); }
// в прототипе ровно 2 метода
alert(Object.getOwnPropertyNames(User.prototype)); // constructor, sayHi@A@
синтаксистик кант эле эмес
Кээде class
бул JavaScript'те жөн эле "синтаксистик кант" деп айтылат (коддун окулушун жакшыртуу үчүн синтаксис, бирок принципиалдуу жаңы эч нерсе жасабайт), анткени биз конструкциясыз бир эле нерсени жасай алабыз class
:
@A@// перепишем класс User на чистых функциях
// 1. Создаём функцию constructor
function User(name) {
this.name = name;
}
// каждый прототип функции имеет свойство constructor по умолчанию,
// поэтому нам нет необходимости его создавать
// 2. Добавляем метод в прототип
User.prototype.sayHi = function() {
alert(this.name);
};
// Использование:
let user = new User("Иван");
user.sayHi();@A@
Бул коддун натыйжасы абдан окшош. class
Ошентип, чындыгында, прототип ыкмалары менен бирге конструкторду аныктоо үчүн синтаксистик кант деп эсептелиши мүмкүн болгон себептер бар .
Бирок, маанилүү айырмачылыктар бар:
-
Биринчиден, менен түзүлгөн функция
class
атайын ички касиет менен белгиленет[[IsClassConstructor]]: true
. Ошондуктан, аны кол менен түзүү так эле бирдей эмес.Кадимки функциялардан айырмаланып, класстын конструкторун төмөнкүчө чакырууга болбойт
new
:@A@class User { constructor() {} } alert(typeof User); // function User(); // Error: Class constructor User cannot be invoked without 'new'@A@
Ошондой эле, көпчүлүк JavaScript кыймылдаткычтарында класс конструкторунун сап чагылдырылышы "класс..." менен башталат.
@A@class User { constructor() {} } alert(User); // class User { ... }@A@
-
Класстын ыкмалары санап болбойт. Класстын аныктамасы бардык ыкмалар үчүн желекти
enumerable
орнотот .false
"prototype"
Бул жакшы, анткени биз
for..in
объект аркылуу цикл болсок, анда биз класстык методдорду алгыбыз келбейт. -
Класстар ар дайым колдонушат
use strict
. Класс ичиндеги бардык код автоматтык түрдө катуу режимде болот.
Ошондой эле, жогоруда сүрөттөлгөн негизги функциялардан тышкары, синтаксис class
дагы бир катар кызыктуу функцияларды берет, алар менен биз кийинчерээк таанышабыз.
класстык билдирүү
Функциялар сыяктуу эле класстар дагы башка туюнтма ичинде аныкталышы мүмкүн, өткөрүлүп берилиши, кайтарылышы, дайындалышы ж.б.у.с.
Класс туюнтмасынын мисалы (Функция туюнтмасына окшош):
@A@let User = class {
sayHi() {
alert("Привет");
}
};@A@
Аты аталган функция туюнтмасы сыяктуу, Класс туюнтмасынын да аты болушу мүмкүн.
Эгерде Класс туюнтмасынын аты болсо, анда ал класстын ичинде гана көрүнөт:
@A@// "Named Class Expression"
// (в спецификации нет такого термина, но происходящее похоже на Named Function Expression)
let User = class MyClass {
sayHi() {
alert(MyClass); // имя MyClass видно только внутри класса
}
};
new User().sayHi(); // работает, выводит определение MyClass
alert(MyClass); // ошибка, имя MyClass не видно за пределами класса@A@
Биз класстарды динамикалык түрдө "талап боюнча" түзө алабыз:
@A@function makeClass(phrase) {
// объявляем класс и возвращаем его
return class {
sayHi() {
alert(phrase);
};
};
}
// Создаём новый класс
let User = makeClass("Привет");
new User().sayHi(); // Привет@A@
Getters/setters, башка аббревиатуралар
Сөзмө-сөз объекттер сыяктуу эле, класстарда эсептелген касиеттерди, алуучуларды/жөндөөчүлөрдү жана башкаларды жарыялай аласыз.
user.name
Бул жерде колдонуу менен ишке ашырылган бир мисал келтирилген get/set
:
@A@class User {
constructor(name) {
// вызывает сеттер
this.name = name;
}
get name() {
return this._name;
}
set name(value) {
if (value.length < 4) {
alert("Имя слишком короткое.");
return;
}
this._name = value;
}
}
let user = new User("Иван");
alert(user.name); // Иван
user = new User(""); // Имя слишком короткое@A@.
Классты жарыялоодо, алуучулар/жөндөөчүлөр User.prototype
төмөнкүдөй түзүлөт:
@A@Object.defineProperties(User.prototype, {
name: {
get() {
return this._name
},
set(name) {
// ...
}
}
});@A@
кашаанын ичинде эсептелген касиети менен мисал [...]
:
@A@class User {
['say' + 'Hi']() {
alert("Привет");
}
}
new User().sayHi();@A@
Класс касиеттери
Класстын касиеттери тилге жакында кошулду.
Жогорудагы мисалда класста User
методдор гана болгон. Мүлктү кошолу:
@A@class User {
name = "Аноним";
sayHi() {
alert(`Привет, ${this.name}!`);
}
}
new User().sayHi();@A@
Мүлк name
белгиленген эмес User.prototype
. Анын ордуна, ал оператор тарабынан конструктор иштетилгенге чейин түзүлөт new
, бул жөн гана объекттин менчиги.
Бардыгы
Класстардын негизги синтаксиси төмөнкүдөй көрүнөт:
@A@class MyClass {
prop = value; // свойство
constructor(...) { // конструктор
// ...
}
method(...) {} // метод
get something(...) {} // геттер
set something(...) {} // сеттер
[Symbol.iterator]() {} // метод с вычисляемым именем (здесь - символом)
// ...
}@A@
MyClass
Техникалык жактан функция (биз деп аныктаган функция constructor
), ал эми методдор, алуучулар жана орнотуучулар MyClass.prototype
.
Кийинки бөлүмдөрдө класстар, анын ичинде тукум куучулук жана башка өзгөчөлүктөр жөнүндө көбүрөөк билебиз.
Tasks
Класс Clock
функционалдык стилде жазылган. Заманбап класс синтаксисин колдонуп, аны кайра жазыңыз.
PS Консолдо саат тыкылдап жатат. Көрүү үчүн ачыңыз.