aboutsummaryrefslogtreecommitdiff
path: root/files/uk/web/javascript/reference/operators/spread_syntax
diff options
context:
space:
mode:
Diffstat (limited to 'files/uk/web/javascript/reference/operators/spread_syntax')
-rw-r--r--files/uk/web/javascript/reference/operators/spread_syntax/index.html253
1 files changed, 253 insertions, 0 deletions
diff --git a/files/uk/web/javascript/reference/operators/spread_syntax/index.html b/files/uk/web/javascript/reference/operators/spread_syntax/index.html
new file mode 100644
index 0000000000..ca9598e9eb
--- /dev/null
+++ b/files/uk/web/javascript/reference/operators/spread_syntax/index.html
@@ -0,0 +1,253 @@
+---
+title: Оператор розкладу
+slug: Web/JavaScript/Reference/Operators/Spread_syntax
+tags:
+ - ECMAScript 2015
+ - JavaScript
+ - Довідка
+translation_of: Web/JavaScript/Reference/Operators/Spread_syntax
+---
+<div>{{jsSidebar("Operators")}}</div>
+
+<p><strong>Оператор розкладу</strong> дозволяє розкласти ітерабельний об'єкт, такий як масив чи рядок, там, де очікується нуль чи більше аргументів (для викликів функцій) чи елементів (для масивних літералів), або розкласти об'єкт там, де очікується нуль або більше пар ключ-значення (для об'єктних літералів).</p>
+
+<div>{{EmbedInteractiveExample("pages/js/expressions-spreadsyntax.html")}}</div>
+
+
+
+<h2 id="Синтаксис">Синтаксис</h2>
+
+<p>Для викликів функцій:</p>
+
+<pre class="syntaxbox notranslate">myFunction(...iterableObj);
+</pre>
+
+<p>Для масивних літералів або рядків:</p>
+
+<pre class="syntaxbox notranslate">[...iterableObj, "4", "п'ять", 6];</pre>
+
+<p>Для об'єктних літералів (нове у ECMAScript 2018):</p>
+
+<pre class="syntaxbox notranslate">let objClone = { ...obj };</pre>
+
+<h2 id="Залишковий_синтаксис_параметри">Залишковий синтаксис (параметри)</h2>
+
+<p>Залишковий синтаксис виглядає так само, як синтаксис розкладання, але використовується для <em>деструктуризації</em> масивів та об'єктів.</p>
+
+<p>В певному сенсі, залишковий синтаксис є протилежністю синтаксису розкладу. Розклад "розпаковує" масив на його окремі елементи, в той час, як залишковий синтаксис збирає множину елементів та "стискає" їх у єдиний елемент. Дивіться {{jsxref("Functions/решта_параметрів", "залишкові параметри", "", 1)}}.</p>
+
+<h2 id="Приклади">Приклади</h2>
+
+<h3 id="Розклад_у_викликах_функцій"><a id="Spread_in_function_calls" name="Spread_in_function_calls">Розклад у викликах функцій</a></h3>
+
+<h4 id="Заміна_apply">Заміна <code>apply()</code></h4>
+
+<p>Зазвичай, {{jsxref("Function.prototype.apply()")}} використовується, коли ви бажаєте використати елементи масиву як аргументи у функції.</p>
+
+<pre class="brush: js notranslate">function myFunction(x, y, z) { }
+const args = [0, 1, 2];
+myFunction.apply(null, args);</pre>
+
+<p>З оператором розкладу наведене можна записати так:</p>
+
+<pre class="brush: js notranslate">function myFunction(x, y, z) { }
+const args = [0, 1, 2];
+myFunction(...args);</pre>
+
+<p>Будь-який аргумент у списку може використати синтаксис розкладу, і він може використовуватись неодноразово.</p>
+
+<pre class="brush: js notranslate">function myFunction(v, w, x, y, z) { }
+const args = [0, 1];
+myFunction(-1, ...args, 2, ...[3]);</pre>
+
+<h4 id="Apply_для_оператора_new">Apply для оператора <code>new</code></h4>
+
+<p>Викликаючи конструктор з {{jsxref("Operators/new", "new")}}, неможливо <strong>прямо</strong> використовувати масив та <code>apply</code> (<code>apply</code> виконує <code>[[Call]]</code>, а не <code>[[Construct]]</code>). Однак, масив можна легко використовувати з <code>new</code> завдяки синтаксису розкладу:</p>
+
+<pre class="brush: js notranslate">const dateFields = [1970, 0, 1]; // 1 Січня 1970
+const d = new Date(...dateFields);
+</pre>
+
+<p>Щоб використати new з масивом параметрів без розкладу, вам довелося б зробити це <strong>опосередковано</strong>, частковим застосуванням:</p>
+
+<pre class="brush: js notranslate">function applyAndNew(constructor, args) {
+ function partial () {
+ return constructor.apply(this, args);
+ };
+ if (typeof constructor.prototype === "object") {
+ partial.prototype = Object.create(constructor.prototype);
+ }
+ return partial;
+}
+
+
+function myConstructor () {
+ console.log("arguments.length: " + arguments.length);
+ console.log(arguments);
+ this.prop1="знач1";
+ this.prop2="знач2";
+};
+
+var myArguments = ["вітаю", "як", "ся", "маєте", "п.", null];
+var myConstructorWithArguments = applyAndNew(myConstructor, myArguments);
+
+console.log(new myConstructorWithArguments);
+// (internal log of myConstructor): arguments.length: 6
+// (internal log of myConstructor): ["вітаю", "як", "ся", "маєте", "п.", null]
+// (log of "new myConstructorWithArguments"): {prop1: "знач1", prop2: "знач2"}</pre>
+
+<h3 id="Розклад_у_масивних_літералах"><a id="Spread_in_array_literals" name="Spread_in_array_literals">Розклад у масивних літералах</a></h3>
+
+<h4 id="Потужніший_масивний_літерал">Потужніший масивний літерал</h4>
+
+<p>Без оператора розкладу, щоб створити новий масив, частиною якого є існуючий масив, літерального синтаксису масивів недостатньо, доводиться використовувати імперативний код з використанням комбінації з {{jsxref("Array.prototype.push", "push()")}}, {{jsxref("Array.prototype.splice", "splice()")}}, {{jsxref("Array.prototype.concat", "concat()")}}, і т. д. З синтаксисом розкладу все стає набагато лаконічнішим:</p>
+
+<pre class="brush: js notranslate">var parts = ['плечі', 'коліна'];
+var lyrics = ['голова', ...parts, 'та', 'пальці'];
+// ["голова", "плечі", "коліна", "та", "пальці"]
+</pre>
+
+<p>Як і розклад аргументів, <code>...</code> може використовуватись будь-де у масивному літералі, і може використовуватись неодноразово.</p>
+
+<h4 id="Копія_масиву">Копія масиву</h4>
+
+<pre class="brush: js notranslate">const arr = [1, 2, 3];
+const arr2 = [...arr]; // як arr.slice()
+
+arr2.push(4);
+// arr2 стає [1, 2, 3, 4]
+// arr залишається незміненим
+</pre>
+
+<div class="blockIndicator note">
+<p><strong>Заувага:</strong> Оператор розкладу ефективно йде на один рівень вглиб при копіюванні масиву. Тому він може бути непридатний для копіювання багатовимірних масивів, як показано у наступному прикладі (те саме з {{jsxref("Object.assign()")}} та розкладом).</p>
+
+<pre class="brush: js example-bad notranslate">const a = [[1], [2], [3]];
+const b = [...a];
+
+b.shift().shift();
+// 1
+
+// О, ні! Тепер масив 'a' також змінився:
+a
+// [[], [2], [3]]</pre>
+</div>
+
+<h4 id="Краще_обєднання_масивів">Краще об'єднання масивів</h4>
+
+<p>Метод {{jsxref("Array.prototype.concat()")}} часто використовується для приєднання масиву в кінець існуючого масиву. Без оператора розкладу це робиться так:</p>
+
+<pre class="brush: js notranslate">const arr1 = [0, 1, 2];
+const arr2 = [3, 4, 5];
+
+// Додати всі елементи з arr2 у arr1
+arr1 = arr1.concat(arr2);</pre>
+
+<p>З оператором розкладу отримуємо:</p>
+
+<pre class="brush: js notranslate">let arr1 = [0, 1, 2];
+let arr2 = [3, 4, 5];
+
+arr1 = [...arr1, ...arr2];
+// arr1 тепер [0, 1, 2, 3, 4, 5]
+// Заувага: Не використовуйте const, це спричинить TypeError (недозволене присвоєння)
+</pre>
+
+<p>Метод {{jsxref("Array.prototype.unshift()")}} часто використовується для додавання масиву значень у початок існуючого масиву. Без оператора розкладу це робиться так:</p>
+
+<pre class="brush: js notranslate">const arr1 = [0, 1, 2];
+const arr2 = [3, 4, 5];
+
+// Подати усі елементи з arr2 до arr1
+Array.prototype.unshift.apply(arr1, arr2)
+
+// arr1 тепер [3, 4, 5, 0, 1, 2]</pre>
+
+<p>З оператором розкладу отримуємо:</p>
+
+<pre class="brush: js notranslate">let arr1 = [0, 1, 2];
+let arr2 = [3, 4, 5];
+
+arr1 = [...arr2, ...arr1];
+// arr1 тепер [3, 4, 5, 0, 1, 2]
+</pre>
+
+<div class="blockIndicator note">
+<p><strong>Заувага</strong>: На відміну від <code>unshift()</code>, цей код створює новий <code>arr1</code>, а не змінює початковий масив <code>arr1</code>.</p>
+</div>
+
+<h3 id="Розклад_у_обєктних_літералах"><a id="Spread_in_object_literals" name="Spread_in_object_literals">Розклад у об'єктних літералах</a></h3>
+
+<p>Пропозиція <a href="https://github.com/tc39/proposal-object-rest-spread">Rest/Spread Properties for ECMAScript</a> (стадія 4) додала розкладені властивості до {{jsxref("Operators/Ініціалізація_об’єктів", "об'єктних літералів", 1)}}. Цей синтаксис копіює особисті, перелічувані властивості наданого об'єкта у новий об'єкт.</p>
+
+<p>Дрібне клонування (без прототипу) чи злиття об'єктів тепер можливе за допомогою синтаксису, коротшого, ніж {{jsxref("Object.assign()")}}.</p>
+
+<pre class="brush: js notranslate">const obj1 = { foo: 'bar', x: 42 };
+const obj2 = { foo: 'baz', y: 13 };
+
+const clonedObj = { ...obj1 };
+// Object { foo: "bar", x: 42 }
+
+const mergedObj = { ...obj1, ...obj2 };
+// Object { foo: "baz", x: 42, y: 13 }</pre>
+
+<p>Зауважте, що {{jsxref("Object.assign()")}} запускає {{jsxref("Functions/set", "сетери")}}, а оператор розкладу ні.</p>
+
+<p>Зауважте, що ви не можете ані замінити, ані імітувати функцію {{jsxref("Object.assign()")}}:</p>
+
+<pre class="brush: js notranslate">let obj1 = { foo: 'bar', x: 42 };
+let obj2 = { foo: 'baz', y: 13 };
+const merge = ( ...objects ) =&gt; ( { ...objects } );
+
+let mergedObj = merge ( obj1, obj2);
+// Object { 0: { foo: 'bar', x: 42 }, 1: { foo: 'baz', y: 13 } }
+
+let mergedObj = merge ( {}, obj1, obj2);
+// Object { 0: {}, 1: { foo: 'bar', x: 42 }, 2: { foo: 'baz', y: 13 } }</pre>
+
+<p>У наведеному прикладі оператор розкладу працює не так, як можна було очікувати: він розкладає <em>масив</em> аргументів у об'єктний літерал, через наявність залишкового параметра.</p>
+
+<h3 id="Тільки_для_ітерабельних_обєктів">Тільки для ітерабельних об'єктів</h3>
+
+<p>Самі по собі об'єкти не є ітерабельними, але вони стають ітерабельними, коли використовуються у масиві, або з функціями перебору, такими як <code>map()</code>, <code>reduce()</code> та <code>assign()</code>. При з'єднанні 2-х об'єктів за допомогою оператору розкладу, вважається, що застосовується функція перебору, коли відбувається з'єднання.</p>
+
+<p>Оператор розкладу (окрім випадку розкладених властивостей) може застосовуватись тільки до <a href="/uk/docs/Web/JavaScript/Reference/Global_Objects/Symbol/iterator">ітерабельних</a> об'єктів:</p>
+
+<pre class="brush: js notranslate">const obj = {'key1': 'value1'};
+const array = [...obj]; // TypeError: obj is not iterable
+</pre>
+
+<h3 id="Розклад_з_великою_кількістю_значень">Розклад з великою кількістю значень</h3>
+
+<p>При використанні оператора розкладу для викликів функцій пам'ятайте про можливість перевищити ліміт кількості аргументів рушія JavaScript. Більше інформації дивіться у статті {{jsxref("Function.prototype.apply", "apply()")}}.</p>
+
+<h2 id="Специфікації">Специфікації</h2>
+
+<table class="standard-table">
+ <thead>
+ <tr>
+ <th scope="col">Специфікація</th>
+ </tr>
+ </thead>
+ <tbody>
+ <tr>
+ <td>{{SpecName('ESDraft', '#sec-array-initializer', 'Array initializer')}}</td>
+ </tr>
+ <tr>
+ <td>{{SpecName('ESDraft', '#sec-object-initializer', 'Object initializer')}}</td>
+ </tr>
+ </tbody>
+</table>
+
+<h2 id="Сумісність_з_веб-переглядачами">Сумісність з веб-переглядачами</h2>
+
+
+
+<p>{{Compat("javascript.operators.spread")}}</p>
+
+<h2 id="Див._також">Див. також</h2>
+
+<ul>
+ <li><a href="/uk/docs/Web/JavaScript/Reference/Functions/решта_параметрів">Залишкові параметри</a> (також ‘<code>...</code>’)</li>
+ <li><a href="/uk/docs/Web/JavaScript/Reference/Global_Objects/Function/apply">fn.apply</a> (також ‘<code>...</code>’)</li>
+</ul>