Як конвертувати Set в масив?


469

Набір здається приємним способом створення масивів із гарантованими унікальними елементами, але він не відкриває жодного хорошого способу отримання властивостей, за винятком генератора [Set] .values, який викликається незграбно mySet.values.next().

Це було б нормально, якби ви могли викликати mapта подібні функції на Sets. Але ви також не можете цього зробити.

Я намагався Array.from, але, схоже, перетворює в масив лише об’єкти, схожі на масив (NodeList та TypedArrays?). Ще одна спроба: Object.keysне працює для Sets, а Set.prototype не має аналогічного статичного методу.

Отже, питання: чи є якийсь зручний вбудований метод створення масиву зі значеннями заданого набору? (Порядок елемента насправді не має значення).

якщо такого варіанту не існує, то, можливо, є приємний ідіоматичний однокласник для цього? наприклад, використання for...ofчи подібне?

Відповіді:


850

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

Дійсно, існує кілька способів перетворення набору в масив :

використовуючи Array.from

let array = Array.from(mySet);

Просто spreadingВстановіть масив

let array = [...mySet];

Старий спосіб моди, повторення та перехід до нового масиву (набори є forEach)

let array = [];
mySet.forEach(v => array.push(v));

Раніше, використовуючи нестандартний, а тепер застарілий синтаксис розуміння масиву:

let array = [v for (v of mySet)];

7
Це не працює в Safari (8) або Chrome (41). Але це працює і в Firefox (35).
425nesp

2
var array = [v for (v of mySet)];не працює в хромі 46
Ерік

18
Я думаю, що найелегантніший спосіб - це просто [...mySet].
Войцех Беднарський

18
@WojciechBednarski l33t не елегантний . Якщо будь-який із прикладів такий, - цеArray.from(mySet);
Буффало

3
Просто хотілося додати, що [...mySet]виникають проблеми під час компіляції за допомогою Typescript (див. Цю проблему ), тому, ймовірно, безпечніше використовувати, Array.from(mySet)якщо ви плануєте найближчим часом перетворитись на Typescript.
Іван Гозалі

65

через https://speakerdeck.com/anguscroll/es6-uncensored від Angus Croll

Виявляється, ми можемо використовувати spreadоператор:

var myArr = [...mySet];

Або, альтернативно, використовуйте Array.from:

var myArr = Array.from(mySet);

1
чому потік? чи є проблеми з таким підходом? Або хтось спробував виконати цей код в IE11 і не вдався ? ;)
c69

6
Я не заявив, але спробував це в останній версії Chrome і не вдався, тому це не лише проблема IE.
Мешаал

3
Зверніться до kangax.github.io/compat-table/es6 для більш-менш актуальної діаграми підтримки. В даний час з усіх настільних браузерів, тільки FF і IE TP (ака Spartan, інакше MS Non-IE браузером) підтримки Array.fromі...
C69

Схоже, Firefox - єдиний браузер, який підтримує Array.from. developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/…
425nesp

1
Тут ви можете ввімкнути це для Chrome. chrome://flags/#enable-javascript-harmonyПам'ятайте, що експериментально не думайте, що це хороше рішення для розробки.
sospedra

12

Якщо припустити, що ви просто використовуєте Setтимчасово для отримання унікальних значень у масиві, а потім перетворення назад у масив, спробуйте скористатися цим:

_.uniq([])

Це залежить від використання підкреслення або л-тир .


На жаль, єдине рішення для крос-броузера
Марко Сулла

6

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

const set = new Set(['a', 'b']);
const values = set.values();
const array = Array.from(values);

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

Редагувати : сьогодні ви можете просто використовувати те, що пропонує @ c69:

const set = new Set(['a', 'b']);
const array = [...set]; // or Array.from(set)

1
Здається, що за допомогою set.entries()ви отримаєте масив пар. Ви можете використовувати set.values()для отримання простого масиву.
Шимон Рахленко

@ShimonRachlenko правда, і користувач про це попросив.
Роланд

2
Можна просто скористатисяvar array = Array.from(set);
Буффало

ця відповідь просто неправильна. Вам не потрібен виклик .entries, ні .values. Як згадував @Buffalo - Array.from(set)досить.
c69

1
@ c69 це правда. На час цієї відповіді Array.from()не працювало так, як очікувалося. Але зараз поширись і Array.from()обидва працюють просто чудово.
Роланд


0

У моєму випадку рішення було:

var testSet = new Set();
var testArray = [];

testSet.add("1");
testSet.add("2");
testSet.add("2"); // duplicate item
testSet.add("3");

var someFunction = function (value1, value2, setItself) {
    testArray.push(value1);
};

testSet.forEach(someFunction);

console.log("testArray: " + testArray);

value1 дорівнює value2 => Значення, що міститься в поточному положенні набору. Для обох аргументів передається однакове значення

Працював під IE11.


0

Використання набору та перетворення його в масив дуже схоже на копіювання масиву ...

Таким чином, ви можете використовувати ті самі методи для копіювання масиву, що дуже просто в ES6

Наприклад, ви можете використовувати ...

Уявіть, що у вас є цей набір нижче:

const a = new Set(["Alireza", "Dezfoolian", "is", "a", "developer"]);

Ви можете просто перетворити його за допомогою:

const b = [...a];

і результат:

["Alireza", "Dezfoolian", "is", "a", "developer"]

Масив, і тепер ви можете використовувати всі методи, які ви можете використовувати для масиву ...

Інші поширені способи:

const b = Array.from(a);

або за допомогою циклів, таких як:

const b = [];
a.forEach(v => b.push(v));

0

Код нижче створює набір з масиву, а потім, використовуючи ...оператор.

var arr=[1,2,3,4,5,6,7,8,9,1,2,3,4,5,6,7,8,9,];
var set=new Set(arr);
let setarr=[...set];
console.log(setarr);

Будь ласка, коментуйте свій код.
Хіма

1
..і це що?
ZF007

-1

Ось простий спосіб отримати лише унікальні неочищені значення з масиву. Якщо ви перетворили масив у Set і після цього, зробіть перетворення з Set в масив. Це перетворення працює лише для необроблених значень, для об'єктів у масиві воно недійсне. Спробуйте самі.

    let myObj1 = {
        name: "Dany",
        age: 35,
        address: "str. My street N5"
    }

    let myObj2 = {
        name: "Dany",
        age: 35,
        address: "str. My street N5"
    }

    var myArray = [55, 44, 65, myObj1, 44, myObj2, 15, 25, 65, 30];
    console.log(myArray);

    var mySet = new Set(myArray);
    console.log(mySet);

    console.log(mySet.size === myArray.length);// !! The size differs because Set has only unique items

    let uniqueArray = [...mySet];
    console.log(uniqueArray); 
    // Here you will see your new array have only unique elements with raw 
    // values. The objects are not filtered as unique values by Set.
    // Try it by yourself.

-1

ПРОСТИЙ ВІДПОВІДЬ

просто розкладіть набір всередину []

let mySet = new Set()
mySet.add(1)
mySet.add(5)
mySet.add(5) 
let arr = [...mySet ]

Результат : [1,5]

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.