Skip to content

Commit 5064472

Browse files
committed
trie 구현
1 parent 03a66b3 commit 5064472

6 files changed

Lines changed: 143 additions & 17 deletions

File tree

Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
// @ts-nocheck
22

33
class TrieNode {
4-
constructor() {
4+
constructor(value = "") {
5+
this.value = value;
56
this.children = new Map();
67
this.pass = 0;
78
this.end = 0;
@@ -10,34 +11,39 @@ class TrieNode {
1011

1112
class Trie {
1213
constructor() {
13-
this.root = new TrieNode();
14-
this.totalWorlds = 0;
14+
this.root = new TrieNode("");
15+
this.totalWords = 0;
1516
}
17+
1618
insert(word) {
1719
let node = this.root;
1820
node.pass++;
1921

2022
for (let i = 0; i < word.length; i++) {
2123
const ch = word[i];
24+
2225
if (!node.children.has(ch)) {
23-
node.children.set(ch, new TrieNode());
26+
node.children.set(ch, new TrieNode(node.value + ch));
2427
}
28+
2529
node = node.children.get(ch);
2630
node.pass++;
2731
}
32+
2833
node.end++;
29-
this.totalWorlds = word.length;
34+
this.totalWords++;
3035
}
3136

3237
#walk(s) {
3338
let node = this.root;
39+
3440
for (let i = 0; i < s.length; i++) {
3541
const ch = s[i];
3642
const next = node.children.get(ch);
3743
if (!next) return null;
38-
3944
node = next;
4045
}
46+
4147
return node;
4248
}
4349

@@ -50,31 +56,36 @@ class Trie {
5056
const node = this.#walk(s);
5157
return node ? node.end : 0;
5258
}
53-
54-
startsWith(s) {
55-
const node = this.#walk(s);
59+
countWordsStartingWith(prefix) {
60+
const node = this.#walk(prefix);
5661
return node ? node.pass : 0;
5762
}
5863

59-
delete(s) {
60-
if (!this.search(s)) return false;
64+
delete(word) {
65+
if (!this.search(word)) return false;
66+
6167
let node = this.root;
6268
node.pass--;
69+
6370
const stack = [];
64-
for (let i = 0; i < s.length; i++) {
65-
const ch = s[i];
71+
for (let i = 0; i < word.length; i++) {
72+
const ch = word[i];
6673
stack.push([node, ch]);
74+
6775
node = node.children.get(ch);
6876
node.pass--;
6977
}
78+
7079
node.end--;
71-
this.totalWorlds--;
80+
this.totalWords--;
81+
7282
for (let i = stack.length - 1; i >= 0; i--) {
7383
const [par, ch] = stack[i];
7484
const child = par.children.get(ch);
7585
if (child.pass === 0) par.children.delete(ch);
7686
else break;
7787
}
88+
7889
return true;
7990
}
8091

@@ -86,7 +97,13 @@ class Trie {
8697
if (node.end > 0) {
8798
res.push(path.join(""));
8899
}
89-
for (const [ch, next] of node.children) {
100+
101+
const entries = Array.from(node.children.entries());
102+
103+
for (let i = 0; i < entries.length; i++) {
104+
const ch = entries[i][0];
105+
const next = entries[i][1];
106+
90107
path.push(ch);
91108
dfs(next);
92109
path.pop();
@@ -97,6 +114,7 @@ class Trie {
97114
return res;
98115
}
99116
}
117+
100118
const trie = new Trie();
101119

102120
trie.insert("flower");
@@ -106,8 +124,8 @@ trie.insert("flow"); // duplicate
106124

107125
console.log(trie.search("flow")); // true
108126
console.log(trie.countWordsEqualTo("flow")); // 2
109-
console.log(trie.startsWith("fl")); // true
127+
console.log(trie.countWordsStartingWith("fl")); // 4 (flower, flow, flight, flow)
110128

111129
trie.delete("flow");
112130
console.log(trie.countWordsEqualTo("flow")); // 1
113-
console.log(trie.words()); // unique words: ["flower","flow","flight"] (again order may vary)
131+
console.log(trie.words()); // ["flight","flow","flower"] (순서는 Map 순서에 따라 달라질 수 있음)
Lines changed: 106 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,106 @@
1+
// @ts-nocheck
2+
class TrieNode {
3+
constructor(val = "") {
4+
this.val = val;
5+
this.children = new Map();
6+
this.pass = 0;
7+
this.isEnd = false;
8+
}
9+
}
10+
class Trie {
11+
constructor() {
12+
this.root = new TrieNode("");
13+
this.totalWords = 0;
14+
}
15+
16+
insert(s) {
17+
let node = this.root;
18+
node.pass++;
19+
for (let i = 0; i < s.length; i++) {
20+
const ch = s[i];
21+
if (!node.children.get(ch)) {
22+
node.children.set(ch, new TrieNode(ch));
23+
}
24+
node = node.children.get(ch);
25+
node.pass++;
26+
}
27+
node.isEnd = true;
28+
this.totalWords = s.length;
29+
}
30+
31+
#walk(s) {
32+
let node = this.root;
33+
for (let i = 0; i < s.length; i++) {
34+
const ch = s[i];
35+
const next = node.children.get(ch);
36+
if (!next) return null;
37+
node = next;
38+
}
39+
return node;
40+
}
41+
42+
search(s) {
43+
const node = this.#walk(s);
44+
return !!node && node.isEnd === true;
45+
}
46+
startWith(s) {
47+
const node = this.#walk(s);
48+
return node ? node.pass : 0;
49+
}
50+
51+
delete(s) {
52+
if (!this.search(s)) return false;
53+
let node = this.root;
54+
const stack = [];
55+
56+
for (let i = 0; i < s.length; i++) {
57+
const ch = s[i];
58+
stack.push([node, ch]);
59+
node = node.children.get(ch);
60+
node.pass--;
61+
}
62+
63+
node.isEnd = false;
64+
this.totalWords--;
65+
66+
for (let i = stack.length - 1; i >= 0; i--) {
67+
const [par, ch] = stack[i];
68+
const child = par.children.get(cj);
69+
if (child.pass === 0) par.children.delete(child);
70+
else break;
71+
}
72+
73+
return true;
74+
}
75+
76+
words() {
77+
const res = [];
78+
const path = [];
79+
const dfs = (node) => {
80+
if (node.isEnd) {
81+
res.push(path.join(""));
82+
}
83+
const entries = Array.from(node.children.entries());
84+
for (let i = 0; i < entries.length; i++) {
85+
const ch = entries[i][0];
86+
const next = entries[i][1];
87+
path.push(ch);
88+
dfs(next);
89+
path.pop();
90+
}
91+
};
92+
dfs(this.root);
93+
return res;
94+
}
95+
}
96+
const trie = new Trie();
97+
98+
trie.insert("flower");
99+
trie.insert("flow");
100+
trie.insert("flight");
101+
trie.insert("flow"); // duplicate
102+
103+
console.log(trie.search("flow")); // true
104+
console.log(trie.startWith("fl")); // 4 (flower, flow, flight, flow)
105+
106+
console.log(trie.words()); // ["flight","flow","flower"] (순서는 Map 순서에 따라 달라질 수 있음)
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
// @ts-nocheck
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+

허현빈/8주차/trie/trie-구현-5.js

Whitespace-only changes.

0 commit comments

Comments
 (0)