@gkucmierz/utils 1.25.0 → 1.26.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package-lock.json CHANGED
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "@gkucmierz/utils",
3
- "version": "1.25.0",
3
+ "version": "1.26.0",
4
4
  "lockfileVersion": 2,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "@gkucmierz/utils",
9
- "version": "1.25.0",
9
+ "version": "1.26.0",
10
10
  "license": "MIT",
11
11
  "devDependencies": {
12
12
  "husky": "^8.0.1",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@gkucmierz/utils",
3
- "version": "1.25.0",
3
+ "version": "1.26.0",
4
4
  "description": "Usefull functions for solving programming tasks",
5
5
  "main": "main.mjs",
6
6
  "scripts": {
@@ -0,0 +1,36 @@
1
+
2
+ import {
3
+ Trie,
4
+ } from '../src/Trie.mjs';
5
+
6
+ describe('Trie', () => {
7
+ it('check empty', () => {
8
+ const trie = Trie();
9
+ expect(trie.has('')).toBe(false);
10
+ expect(trie.has('abc')).toBe(false);
11
+ });
12
+
13
+ it('init data', () => {
14
+ const trie = Trie(['abc', '']);
15
+ expect(trie.has('')).toBe(true);
16
+ expect(trie.has('abc')).toBe(true);
17
+ });
18
+
19
+ it('add/readd data', () => {
20
+ const trie = Trie();
21
+ expect(trie.has('')).toBe(false);
22
+ expect(trie.add('')).toBe(true);
23
+ expect(trie.has('')).toBe(true);
24
+ expect(trie.add('')).toBe(false);
25
+ });
26
+
27
+ it('list data', () => {
28
+ const trie = Trie(['abc', '', 'abcdef', 'xyz']);
29
+ const abc = ['abc', 'abcdef'];
30
+ expect(trie.get('a')).toEqual(abc);
31
+ expect(trie.get('ab')).toEqual(abc);
32
+ expect(trie.get('abc')).toEqual(abc);
33
+ expect(trie.get('aa')).toEqual([]);
34
+ expect(trie.get('')).toEqual(['', 'abc', 'abcdef', 'xyz']);
35
+ });
36
+ });
package/src/Trie.mjs ADDED
@@ -0,0 +1,45 @@
1
+
2
+ export const Trie = (words = []) => {
3
+ const HAS = 0;
4
+ const MAP = 1;
5
+ const data = [false, new Map()];
6
+ const add = word => {
7
+ let node = data;
8
+ for (let i = 0; i < word.length; ++i) {
9
+ const char = word[i];
10
+ if (!node[MAP]) node[MAP] = new Map();
11
+ const child = node[MAP].get(char) ?? [false];
12
+ node[MAP].set(char, child);
13
+ node = child;
14
+ }
15
+ if (node[HAS]) return false;
16
+ node[HAS] = true;
17
+ return true;
18
+ };
19
+ const findNode = word => {
20
+ let node = data;
21
+ for (let i = 0; i < word.length; ++i) {
22
+ const char = word[i];
23
+ if (!node[MAP]?.has(char)) return [false];
24
+ node = node[MAP].get(char);
25
+ }
26
+ return node;
27
+ };
28
+ const has = word => findNode(word)[HAS];
29
+ const get = begin => {
30
+ const res = [];
31
+ const loop = (node, str = '') => {
32
+ if (!node) return;
33
+ if (node[HAS]) res.push(begin + str);
34
+ const map = node[MAP] || new Map();
35
+ [...map].map(([char, node]) => loop(node, str + char));
36
+ };
37
+ loop(findNode(begin));
38
+ return res;
39
+ };
40
+ words.map(word => add(word));
41
+ return {
42
+ add, has, get,
43
+ getData: () => data,
44
+ };
45
+ };