Внедрение JavaScript в заданной структуре данных
Я ищу достойную реализацию установленной структуры данных в JavaScript. Он должен иметь возможность поддерживать элементы, которые являются обычными объектами JavaScript.
До сих пор я нашел Closure Library structs.Set, но мне не нравится тот факт, что он меняет мои данные.
Любые идеи?
Ответы
Ответ 1
Вы можете создать простую оболочку вокруг ключей хэш-таблицы, предоставленной моим jshashtable. У меня есть кто-то, кто-то стучит куда-нибудь, что я выкапываю позже.
UPDATE
Я завершил и протестировал реализацию HashSet и загрузил ее в проект jshashtable в Google Code. Вы можете загрузить его или просмотреть источник.
var s = new HashSet();
var o1 = {name: "One"}, o2 = {name: "Two"};
s.add(o1);
s.add(o2);
s.values(); // Array containing o1 and o2
Ответ 2
В ECMAScript 6 есть
Spec: http://www.ecma-international.org/ecma-262/6.0/#sec-set-constructor
Использование: https://github.com/lukehoban/es6features#map--set--weakmap--weakset
Пример:
var s = new Set()
s.add("hello").add("goodbye").add("hello")
s.size === 2
s.has("hello") === true
Модуль, который реализует его для браузеров без поддержки: https://github.com/medikoo/es6-set
Ответ 3
Используйте стандартную структуру данных ECMAScript 2015 (ES6), которая проста в использовании:
var mySet = new Set();
mySet.add(1);
mySet.add(5);
mySet.add("some text");
var o = {a: 1, b: 2};
mySet.add(o);
mySet.has(1); // true
mySet.has(3); // false, 3 has not been added to the set
mySet.has(5); // true
mySet.has(Math.sqrt(25)); // true
mySet.has("Some Text".toLowerCase()); // true
mySet.has(o); // true
mySet.size; // 4
mySet.delete(5); // removes 5 from the set
mySet.has(5); // false, 5 has been removed
mySet.size; // 3, we just removed one value
Обновление для тех, кто использует AngularJs
Имейте в виду, что набор не работает с ng-repeat
. Так что лучше использовать массив и просто применить уникальный фильтр
Ответ 4
Я не думаю, что есть способ работать с хеш-кодом объекта, кроме сохранения его в самом объекте. Строго говоря, можно создать заданный класс без хеширования, используя простой линейный поиск, но это вряд ли будет эффективным.
Ответ 5
Мне нравится Simple-JS-Set (возможно, потому, что я его написал). Он поддерживает любой объект JavaScript. Он имеет следующий API:
-
Set(hashFunction)
: (Конструктор) Создайте новый набор с заданным hashFunction
(по умолчанию JSON.stringify
)
-
add(item)
: добавьте элемент в набор
-
remove(item)
: удалить элемент из набора
-
contains(item)
: Возвращает, содержится ли элемент в наборе
-
size()
: Возвращает количество уникальных элементов в наборе
-
each(function(item), thisObj)
: выполнить функцию с каждым элементом в наборе в thisObj
Ответ 6
В ES6 версии Javascript вы создали тип для set (проверьте совместимость с вашим браузером).
var numbers = new Set([1, 2, 4]); // Set {1, 2, 4}
Чтобы добавить элемент в набор, который вы просто используете .add()
, который работает в O(1)
, и либо добавляет элемент для установки (если он не существует), либо ничего не делает, если он уже здесь. Вы можете добавить туда элемент любого типа (массивы, строки, числа)
numbers.add(4); // Set {1, 2, 4}
numbers.add(6); // Set {1, 2, 4, 6}
Чтобы проверить количество элементов в наборе, вы можете просто использовать .size
. Также работает в O(1)
numbers.size; // 4
Чтобы удалить элемент из набора, используйте .delete()
. Он возвращает true, если значение было (и было удалено), а false, если значение не было. Также работает в O(1)
.
numbers.delete(2); // true
numbers.delete(2); // false
Чтобы проверить, существует ли элемент в наборе, используйте .has()
, который возвращает true, если элемент находится в наборе, а false - в противном случае. Также работает в O(1)
.
numbers.has(3); // false
numbers.has(1); // true
В дополнение к методам, которые вы хотели, есть несколько дополнительных:
-
numbers.clear();
просто удалит все элементы из набора
-
numbers.forEach(callback);
итерация через значения набора в порядке размещения
-
numbers.entries();
создать итератор всех значений
-
numbers.keys();
возвращает ключи набора, которые совпадают с numbers.values()
Существует также Weakset, который позволяет добавлять только значения типа объекта.