You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
The first kind is *data properties*. We already know how to work with them. All properties that we've been using until now were data properties.
6
+
Перший вид *властивості даних (data properties)*. Ми вже знаємо, як працювати з ними. Всі властивості, які ми використовували дотепер, були властивостями даних.
7
7
8
-
The second type of properties is something new. It's *accessor properties*. They are essentially functions that execute on getting and setting a value, but look like regular properties to an external code.
8
+
Другий вид властивостей -- це щось нове. Це *властивості аксесорів*. Вони по суті функції, які виконуються при отриманні та встановленні значення, але виглядають як звичайні властивості в зовнішньому коді.
9
9
10
-
## Getters and setters
10
+
## Гетери та сетери
11
11
12
-
Accessor properties are represented by "getter" and "setter" methods. In an object literal they are denoted by `get`and`set`:
12
+
Властивості аксесорів представлені методами "гетер" та "сетер". У об’єкті вони буквально позначаються як `get`і`set`:
13
13
14
14
```js
15
15
let obj = {
16
16
*!*get propName()*/!* {
17
-
//getter, the code executed on getting obj.propName
17
+
//гетер, код виконано під час отримання obj.propName
18
18
},
19
19
20
20
*!*set propName(value)*/!* {
21
-
//setter, the code executed on setting obj.propName = value
21
+
//сетер, код виконано під час встановлення obj.propName = value
22
22
}
23
23
};
24
24
```
25
25
26
-
The getter works when `obj.propName`is read, the setter -- when it is assigned.
26
+
Гетер працює, коли `obj.propName`зчитується, сетер -- коли він призначається.
27
27
28
-
For instance, we have a `user`object with `name`and`surname`:
28
+
Наприклад, у нас є об’єкт `user`з `name`і`surname`:
29
29
30
30
```js
31
31
let user = {
32
-
name:"John",
33
-
surname:"Smith"
32
+
name:"Іван",
33
+
surname:"Іванов"
34
34
};
35
35
```
36
36
37
-
Now we want to add a `fullName` property, that should be`"John Smith"`. Of course, we don't want to copy-paste existing information, so we can implement it as an accessor:
37
+
Тепер ми хочемо додати властивість `fullName`, яка повинна бути`"John Smith"`. Звичайно, ми не хочемо копіювати інформацію, що існує, тому ми можемо реалізувати її як аксесор:
38
38
39
39
```js run
40
40
let user = {
41
-
name:"John",
42
-
surname:"Smith",
41
+
name:"Іван",
42
+
surname:"Іванов",
43
43
44
44
*!*
45
45
getfullName() {
@@ -49,13 +49,13 @@ let user = {
49
49
};
50
50
51
51
*!*
52
-
alert(user.fullName); //John Smith
52
+
alert(user.fullName); //Іван Іванов
53
53
*/!*
54
54
```
55
55
56
-
From the outside, an accessor property looks like a regular one. That's the idea of accessor properties. We don't *call*`user.fullName` as a function, we *read* it normally: the getter runs behind the scenes.
56
+
Ззовні аксесор виглядає як звичайна властивість. В цьому і є ідея аксесорів властивостей. Ми не *викликаємо*`user.fullname` як функцію, ми *читаємо* її як звичайну властивість: гетер виконає свою роботу за кулісами.
57
57
58
-
As of now, `fullName` has only a getter. If we attempt to assign `user.fullName=`, there will be an error:
58
+
Зараз `fullname` має тільки гетер. Якщо ми намагаємося присвоїти `user.fullName=`, буде помилка:
59
59
60
60
```js run
61
61
let user = {
@@ -65,16 +65,16 @@ let user = {
65
65
};
66
66
67
67
*!*
68
-
user.fullName="Test"; //Error (property has only a getter)
68
+
user.fullName="Test"; //Помилка (властивість має лише гетер)
69
69
*/!*
70
70
```
71
71
72
-
Let's fix it by adding a setter for`user.fullName`:
72
+
Виправимо це, додавши сетер для`user.fullName`:
73
73
74
74
```js run
75
75
let user = {
76
-
name:"John",
77
-
surname:"Smith",
76
+
name:"Іван",
77
+
surname:"Іванов",
78
78
79
79
getfullName() {
80
80
return`${this.name}${this.surname}`;
@@ -87,34 +87,34 @@ let user = {
87
87
*/!*
88
88
};
89
89
90
-
//set fullName is executed with the given value.
91
-
user.fullName="Alice Cooper";
90
+
//виконується встановлення повного ім’я із заданим значенням.
91
+
user.fullName="Аліса Бондар";
92
92
93
-
alert(user.name); //Alice
94
-
alert(user.surname); //Cooper
93
+
alert(user.name); //Аліса
94
+
alert(user.surname); //Бондар
95
95
```
96
96
97
-
As the result, we have a "virtual" property`fullName`. It is readable and writable.
97
+
Як результат, у нас є "віртуальна" властивість`fullName`. Вона читається і записується.
98
98
99
-
## Accessor descriptors
99
+
## Дескриптори аксесорів
100
100
101
-
Descriptors for accessor properties are different from those for data properties.
101
+
Дескриптори для аксесорів властивостей відрізняються від дескрипторів для властивостей даних.
102
102
103
-
For accessor properties, there is no `value`or`writable`, but instead there are`get`and`set`functions.
103
+
Для аксесорів властивостей немає `value`або`writable`, але замість цього є`get`і`set`функції.
104
104
105
-
That is, an accessor descriptor may have:
105
+
Тобто, дескриптор аксесорів може мати:
106
106
107
-
-**`get`** -- a function without arguments, that works when a property is read,
108
-
-**`set`** -- a function with one argument, that is called when the property is set,
109
-
-**`enumerable`** -- same as for data properties,
110
-
-**`configurable`** -- same as for data properties.
107
+
-**`get`** -- функція без аргументів, що працює, коли читається властивість,
108
+
-**`set`** -- функція з одним аргументом, що викликається, коли встановлюється властивість,
109
+
-**`enumerable`** -- теж саме, що і для властивостей даних,
110
+
-**`configurable`** -- теж саме, що і для властивостей даних.
111
111
112
-
For instance, to create an accessor `fullName`with`defineProperty`, we can pass a descriptor with `get`and`set`:
112
+
Наприклад, щоб створити аксесори `fullName`з`defineProperty`, ми можемо передати дескриптор з `get`і`set`:
Getters/setters can be used as wrappers over "real" property values to gain more control over operations with them.
156
+
Гетери/сетери можуть бути використані як обгортки над "реальними" значеннями властивостей, щоб отримати більше контролю над операціями з ними.
157
157
158
-
For instance, if we want to forbid too short names for `user`, we can have a setter `name`and keep the value in a separate property`_name`:
158
+
Наприклад, якщо ми хочемо заборонити занадто короткі імена для `user`, ми можемо мати сетер `name`і зберігати значення в окремій властивості`_name`:
159
159
160
160
```js run
161
161
let user = {
@@ -165,67 +165,67 @@ let user = {
165
165
166
166
setname(value) {
167
167
if (value.length<4) {
168
-
alert("Name is too short, need at least 4 characters");
168
+
alert("Ім’я занадто коротке, потрібно щонайменше 4 символи");
169
169
return;
170
170
}
171
171
this._name= value;
172
172
}
173
173
};
174
174
175
-
user.name="Pete";
176
-
alert(user.name); //Pete
175
+
user.name="Петро";
176
+
alert(user.name); //Петро
177
177
178
-
user.name=""; //Name is too short...
178
+
user.name=""; //Ім’я занадто коротке...
179
179
```
180
180
181
-
So, the name is stored in `_name` property, and the access is done via getter and setter.
181
+
Отже, ім’я зберігається у властивості `_name`, а доступ виконується за допомогою гетера та сетера.
182
182
183
-
Technically, external code is able to access the name directly by using `user._name`. But there is a widely known convention that properties starting with an underscore `"_"` are internal and should not be touched from outside the object.
183
+
Технічно зовнішній код може мати доступ до ім’я безпосередньо за допомогою `user._name`. Але існує широко відома конвенція, що властивості, що починаються з підкреслення `"_"`, є внутрішніми і не повинні використовуватися ззовні об’єкта.
184
184
185
185
186
-
## Using for compatibility
186
+
## Використання для сумісності
187
187
188
-
One of the great uses of accessors is that they allow to take control over a "regular" data property at any moment by replacing it with a getter and a setter and tweak its behavior.
188
+
Одним з чудових прикладів використання аксесорів полягає у тому, що вони дозволяють контролювати "звичайну" властивість даних в будь-який момент, замінюючи її гетером і сетером і налаштовуючи її поведінку.
189
189
190
-
Imagine we started implementing user objects using data properties `name`and`age`:
190
+
Уявіть, що ми почали реалізувати об’єкти користувача за допомогою властивостей даних `name`та`age`:
191
191
192
192
```js
193
193
functionUser(name, age) {
194
194
this.name= name;
195
195
this.age= age;
196
196
}
197
197
198
-
let john =newUser("John", 25);
198
+
let john =newUser("Іван", 25);
199
199
200
200
alert( john.age ); // 25
201
201
```
202
202
203
-
...But sooner or later, things may change. Instead of `age`we may decide to store `birthday`, because it's more precise and convenient:
203
+
...Але рано чи пізно, речі можуть змінюватися. Замість `age`ми можемо вирішити зберігати `birthday`, тому що це точніше і зручніше:
204
204
205
205
```js
206
206
functionUser(name, birthday) {
207
207
this.name= name;
208
208
this.birthday= birthday;
209
209
}
210
210
211
-
let john =newUser("John", newDate(1992, 6, 1));
211
+
let john =newUser("Іван", newDate(1992, 6, 1));
212
212
```
213
213
214
-
Now what to do with the old code that still uses`age` property?
214
+
Тепер, що робити зі старим кодом, який все ще використовує властивість`age`?
215
215
216
-
We can try to find all such places and fix them, but that takes time and can be hard to do if that code is used by many other people. And besides, `age`is a nice thing to have in `user`, right?
216
+
Ми можемо спробувати знайти всі такі місця та виправити їх, але це вимагає часу, і це може бути важко зробити, якщо цей код використовується багатьма іншими людьми. І, крім того, `age`-- це гарна властивість для `user`, правильно?
217
217
218
-
Let's keep it.
218
+
Залишмо його.
219
219
220
-
Adding a getter for `age`solves the problem:
220
+
Додавання гетера для `age`розв’язує проблему:
221
221
222
222
```js run no-beautify
223
223
functionUser(name, birthday) {
224
224
this.name= name;
225
225
this.birthday= birthday;
226
226
227
227
*!*
228
-
//age is calculated from the current date and birthday
228
+
//вік розраховується з поточної дати та дня народження
229
229
Object.defineProperty(this, "age", {
230
230
get() {
231
231
let todayYear =newDate().getFullYear();
@@ -235,10 +235,10 @@ function User(name, birthday) {
235
235
*/!*
236
236
}
237
237
238
-
let john =newUser("John", newDate(1992, 6, 1));
238
+
let john =newUser("Іван", newDate(1992, 6, 1));
239
239
240
-
alert( john.birthday ); //birthday is available
241
-
alert( john.age ); // ...as well as the age
240
+
alert( john.birthday ); //день народження доступний
241
+
alert( john.age ); // ...так само, як і вік
242
242
```
243
243
244
-
Now the old code works too and we've got a nice additional property.
244
+
Тепер старий код теж працює, і у нас є гарна додаткова властивість.
0 commit comments