@byloth/core 2.0.0-rc.9 → 2.0.1
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/dist/core.js +4087 -621
- package/dist/core.js.map +1 -1
- package/dist/core.umd.cjs +2 -2
- package/dist/core.umd.cjs.map +1 -1
- package/package.json +17 -13
- package/src/core/types.ts +41 -0
- package/src/helpers.ts +11 -2
- package/src/index.ts +12 -9
- package/src/models/aggregators/aggregated-async-iterator.ts +920 -21
- package/src/models/aggregators/aggregated-iterator.ts +838 -22
- package/src/models/aggregators/reduced-iterator.ts +827 -11
- package/src/models/aggregators/types.ts +153 -10
- package/src/models/callbacks/callable-object.ts +42 -6
- package/src/models/callbacks/index.ts +2 -2
- package/src/models/callbacks/publisher.ts +160 -4
- package/src/models/callbacks/switchable-callback.ts +230 -23
- package/src/models/callbacks/types.ts +16 -0
- package/src/models/exceptions/core.ts +132 -3
- package/src/models/exceptions/index.ts +405 -13
- package/src/models/index.ts +4 -8
- package/src/models/iterators/smart-async-iterator.ts +827 -22
- package/src/models/iterators/smart-iterator.ts +755 -20
- package/src/models/iterators/types.ts +268 -9
- package/src/models/json/json-storage.ts +508 -110
- package/src/models/json/types.ts +10 -1
- package/src/models/promises/deferred-promise.ts +85 -5
- package/src/models/promises/index.ts +1 -3
- package/src/models/promises/smart-promise.ts +272 -4
- package/src/models/promises/timed-promise.ts +43 -1
- package/src/models/promises/types.ts +84 -2
- package/src/models/timers/clock.ts +109 -19
- package/src/models/timers/countdown.ts +176 -21
- package/src/models/timers/game-loop.ts +266 -0
- package/src/models/timers/index.ts +2 -1
- package/src/models/types.ts +6 -5
- package/src/utils/async.ts +43 -0
- package/src/utils/curve.ts +85 -0
- package/src/utils/date.ts +204 -10
- package/src/utils/dom.ts +16 -2
- package/src/utils/index.ts +3 -2
- package/src/utils/iterator.ts +200 -17
- package/src/utils/math.ts +55 -3
- package/src/utils/random.ts +139 -2
- package/src/utils/string.ts +11 -0
- package/src/models/game-loop.ts +0 -83
- package/src/models/promises/long-running-task.ts +0 -294
- package/src/models/promises/thenable.ts +0 -97
|
@@ -3,21 +3,161 @@ import { SmartIterator } from "../iterators/index.js";
|
|
|
3
3
|
import type { GeneratorFunction } from "../iterators/types.js";
|
|
4
4
|
|
|
5
5
|
import AggregatedIterator from "./aggregated-iterator.js";
|
|
6
|
-
import type { KeyedIteratee, KeyedReducer,
|
|
6
|
+
import type { KeyedIteratee, KeyedReducer, KeyedTypeGuardPredicate } from "./types.js";
|
|
7
7
|
|
|
8
|
+
/**
|
|
9
|
+
* A class representing an aggregated iterator that has been reduced in a lazy and optimized way.
|
|
10
|
+
*
|
|
11
|
+
* It's part of the {@link AggregatedIterator} and {@link AggregatedAsyncIterator} implementations,
|
|
12
|
+
* providing a way to reduce them into a single value or another aggregated iterable.
|
|
13
|
+
* For this reason, it isn't recommended to instantiate this class directly
|
|
14
|
+
* (although it's still possible), but rather use the reducing methods provided by the aggregated iterators.
|
|
15
|
+
*
|
|
16
|
+
* It isn't directly iterable, just like its parent class, and needs to specify on what you want to iterate.
|
|
17
|
+
* See the {@link ReducedIterator.keys}, {@link ReducedIterator.entries}
|
|
18
|
+
* & {@link ReducedIterator.values} methods.
|
|
19
|
+
* It does, however, provide the same set of methods to perform
|
|
20
|
+
* operations and transformation on the elements of the iterator,
|
|
21
|
+
* having also the knowledge and context of the groups to which
|
|
22
|
+
* they belong, allowing to handle them in a grouped manner.
|
|
23
|
+
*
|
|
24
|
+
* This is particularly useful when you have group elements and
|
|
25
|
+
* need perform specific operations on the reduced elements.
|
|
26
|
+
*
|
|
27
|
+
* ```ts
|
|
28
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
29
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
30
|
+
* .count();
|
|
31
|
+
*
|
|
32
|
+
* console.log(results.toObject()); // { odd: 4, even: 4 }
|
|
33
|
+
* ```
|
|
34
|
+
*
|
|
35
|
+
* @template K The type of the key used to group the elements.
|
|
36
|
+
* @template T The type of the elements in the iterator.
|
|
37
|
+
*/
|
|
8
38
|
export default class ReducedIterator<K extends PropertyKey, T>
|
|
9
39
|
{
|
|
40
|
+
/**
|
|
41
|
+
* The internal {@link SmartIterator} object that holds the reduced elements.
|
|
42
|
+
*/
|
|
10
43
|
protected _elements: SmartIterator<[K, T]>;
|
|
11
44
|
|
|
45
|
+
/**
|
|
46
|
+
* Initializes a new instance of the {@link ReducedIterator} class.
|
|
47
|
+
*
|
|
48
|
+
* ---
|
|
49
|
+
*
|
|
50
|
+
* @example
|
|
51
|
+
* ```ts
|
|
52
|
+
* const results = new ReducedIterator<string, number>([["A", 1], ["B", 2], ["C", 4]]);
|
|
53
|
+
* ```
|
|
54
|
+
*
|
|
55
|
+
* ---
|
|
56
|
+
*
|
|
57
|
+
* @param iterable A reduced iterable object.
|
|
58
|
+
*/
|
|
12
59
|
public constructor(iterable: Iterable<[K, T]>);
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Initializes a new instance of the {@link ReducedIterator} class.
|
|
63
|
+
*
|
|
64
|
+
* ---
|
|
65
|
+
*
|
|
66
|
+
* @example
|
|
67
|
+
* ```ts
|
|
68
|
+
* const results = new ReducedIterator<string, number>({
|
|
69
|
+
* _index: 0,
|
|
70
|
+
* next: () =>
|
|
71
|
+
* {
|
|
72
|
+
* if (this._index >= 3) { return { done: true, value: undefined }; }
|
|
73
|
+
* this._index += 1;
|
|
74
|
+
*
|
|
75
|
+
* return { done: false, value: [["A", "B", "C"][this._index], (this._index + 1)] };
|
|
76
|
+
* }
|
|
77
|
+
* });
|
|
78
|
+
* ```
|
|
79
|
+
*
|
|
80
|
+
* ---
|
|
81
|
+
*
|
|
82
|
+
* @param iterator An reduced iterator object.
|
|
83
|
+
*/
|
|
13
84
|
public constructor(iterator: Iterator<[K, T]>);
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* Initializes a new instance of the {@link ReducedIterator} class.
|
|
88
|
+
*
|
|
89
|
+
* ---
|
|
90
|
+
*
|
|
91
|
+
* @example
|
|
92
|
+
* ```ts
|
|
93
|
+
* import { range, Random } from "@byloth/core";
|
|
94
|
+
*
|
|
95
|
+
* const results = new ReducedIterator<string, number>(function* ()
|
|
96
|
+
* {
|
|
97
|
+
* for (const index of range(3))
|
|
98
|
+
* {
|
|
99
|
+
* yield [["A", "B", "C"][index], (index + 1)];
|
|
100
|
+
* }
|
|
101
|
+
* });
|
|
102
|
+
* ```
|
|
103
|
+
*
|
|
104
|
+
* ---
|
|
105
|
+
*
|
|
106
|
+
* @param generatorFn A generator function that produces the reduced elements.
|
|
107
|
+
*/
|
|
14
108
|
public constructor(generatorFn: GeneratorFunction<[K, T]>);
|
|
109
|
+
|
|
110
|
+
/**
|
|
111
|
+
* Initializes a new instance of the {@link ReducedIterator} class.
|
|
112
|
+
*
|
|
113
|
+
* ---
|
|
114
|
+
*
|
|
115
|
+
* @example
|
|
116
|
+
* ```ts
|
|
117
|
+
* const results = new ReducedIterator(reducedValues);
|
|
118
|
+
* ```
|
|
119
|
+
*
|
|
120
|
+
* ---
|
|
121
|
+
*
|
|
122
|
+
* @param argument An iterable, iterator or generator function that produces the reduced elements.
|
|
123
|
+
*/
|
|
15
124
|
public constructor(argument: Iterable<[K, T]> | Iterator<[K, T]> | GeneratorFunction<[K, T]>);
|
|
16
125
|
public constructor(argument: Iterable<[K, T]> | Iterator<[K, T]> | GeneratorFunction<[K, T]>)
|
|
17
126
|
{
|
|
18
127
|
this._elements = new SmartIterator(argument);
|
|
19
128
|
}
|
|
20
129
|
|
|
130
|
+
/**
|
|
131
|
+
* Determines whether all elements of the reduced iterator satisfy the given condition.
|
|
132
|
+
* See also {@link ReducedIterator.some}.
|
|
133
|
+
*
|
|
134
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
135
|
+
* Once a single element doesn't satisfy the condition, the method will return `false` immediately.
|
|
136
|
+
*
|
|
137
|
+
* This may lead to an unknown final state of the iterator, which may be entirely or partially consumed.
|
|
138
|
+
* For this reason, it's recommended to consider it as consumed in any case and to not use it anymore.
|
|
139
|
+
* Consider using {@link ReducedIterator.find} instead.
|
|
140
|
+
*
|
|
141
|
+
* If the iterator is infinite and every element satisfies the condition, the method will never return.
|
|
142
|
+
*
|
|
143
|
+
* ---
|
|
144
|
+
*
|
|
145
|
+
* @example
|
|
146
|
+
* ```ts
|
|
147
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
148
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
149
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
150
|
+
* .every((key, value) => value > 0);
|
|
151
|
+
*
|
|
152
|
+
* console.log(results); // true
|
|
153
|
+
* ```
|
|
154
|
+
*
|
|
155
|
+
* ---
|
|
156
|
+
*
|
|
157
|
+
* @param predicate The condition to check for each element of the iterator.
|
|
158
|
+
*
|
|
159
|
+
* @returns `true` if all elements satisfy the condition, `false` otherwise.
|
|
160
|
+
*/
|
|
21
161
|
public every(predicate: KeyedIteratee<K, T, boolean>): boolean
|
|
22
162
|
{
|
|
23
163
|
for (const [index, [key, element]] of this._elements.enumerate())
|
|
@@ -27,6 +167,38 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
27
167
|
|
|
28
168
|
return true;
|
|
29
169
|
}
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* Determines whether any element of the reduced iterator satisfies the given condition.
|
|
173
|
+
* See also {@link ReducedIterator.every}.
|
|
174
|
+
*
|
|
175
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
176
|
+
* Once a single element satisfies the condition, the method will return `true` immediately.
|
|
177
|
+
*
|
|
178
|
+
* This may lead to an unknown final state of the iterator, which may be entirely or partially consumed.
|
|
179
|
+
* For this reason, it's recommended to consider it as consumed in any case and to not use it anymore.
|
|
180
|
+
* Consider using {@link ReducedIterator.find} instead.
|
|
181
|
+
*
|
|
182
|
+
* If the iterator is infinite and no element satisfies the condition, the method will never return.
|
|
183
|
+
*
|
|
184
|
+
* ---
|
|
185
|
+
*
|
|
186
|
+
* @example
|
|
187
|
+
* ```ts
|
|
188
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
189
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
190
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
191
|
+
* .some((key, value) => value > 0);
|
|
192
|
+
*
|
|
193
|
+
* console.log(results); // true
|
|
194
|
+
* ```
|
|
195
|
+
*
|
|
196
|
+
* ---
|
|
197
|
+
*
|
|
198
|
+
* @param predicate The condition to check for each element of the iterator.
|
|
199
|
+
*
|
|
200
|
+
* @returns `true` if any element satisfies the condition, `false` otherwise.
|
|
201
|
+
*/
|
|
30
202
|
public some(predicate: KeyedIteratee<K, T, boolean>): boolean
|
|
31
203
|
{
|
|
32
204
|
for (const [index, [key, element]] of this._elements.enumerate())
|
|
@@ -37,8 +209,77 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
37
209
|
return false;
|
|
38
210
|
}
|
|
39
211
|
|
|
212
|
+
/**
|
|
213
|
+
* Filters the elements of the reduced iterator using a given condition.
|
|
214
|
+
*
|
|
215
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
216
|
+
* If the condition is met, the element will be included in the new iterator.
|
|
217
|
+
*
|
|
218
|
+
* Since the iterator is lazy, the filtering process will
|
|
219
|
+
* be executed once the resulting iterator is materialized.
|
|
220
|
+
*
|
|
221
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
222
|
+
* This means that the original iterator won't be consumed until the
|
|
223
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
224
|
+
*
|
|
225
|
+
* ---
|
|
226
|
+
*
|
|
227
|
+
* @example
|
|
228
|
+
* ```ts
|
|
229
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
230
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
231
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
232
|
+
* .filter((key, value) => value > 0);
|
|
233
|
+
*
|
|
234
|
+
* console.log(results.toObject()); // { odd: 4, even: 16 }
|
|
235
|
+
* ```
|
|
236
|
+
*
|
|
237
|
+
* ---
|
|
238
|
+
*
|
|
239
|
+
* @param predicate The condition to check for each element of the iterator.
|
|
240
|
+
*
|
|
241
|
+
* @returns A new {@link ReducedIterator} containing only the elements that satisfy the condition.
|
|
242
|
+
*/
|
|
40
243
|
public filter(predicate: KeyedIteratee<K, T, boolean>): ReducedIterator<K, T>;
|
|
41
|
-
|
|
244
|
+
|
|
245
|
+
/**
|
|
246
|
+
* Filters the elements of the reduced iterator using a given type guard predicate.
|
|
247
|
+
*
|
|
248
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
249
|
+
* If the condition is met, the element will be included in the new iterator.
|
|
250
|
+
*
|
|
251
|
+
* Since the iterator is lazy, the filtering process will
|
|
252
|
+
* be executed once the resulting iterator is materialized.
|
|
253
|
+
*
|
|
254
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
255
|
+
* This means that the original iterator won't be consumed until the
|
|
256
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
257
|
+
*
|
|
258
|
+
* ---
|
|
259
|
+
*
|
|
260
|
+
* @example
|
|
261
|
+
* ```ts
|
|
262
|
+
* const results = new SmartIterator<number | string>([-3, -1, "0", "2", 3, 5, "6", "8"])
|
|
263
|
+
* .groupBy((value) => Number(value) % 2 === 0 ? "even" : "odd")
|
|
264
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
265
|
+
* .filter<number>((key, value) => typeof value === "number");
|
|
266
|
+
*
|
|
267
|
+
* console.log(results.toObject()); // { odd: 4 }
|
|
268
|
+
* ```
|
|
269
|
+
*
|
|
270
|
+
* ---
|
|
271
|
+
*
|
|
272
|
+
* @template S
|
|
273
|
+
* The type of the elements that satisfy the condition.
|
|
274
|
+
* This allows the type-system to infer the correct type of the iterator.
|
|
275
|
+
*
|
|
276
|
+
* It must be a subtype of the original type of the elements.
|
|
277
|
+
*
|
|
278
|
+
* @param predicate The type guard condition to check for each element of the iterator.
|
|
279
|
+
*
|
|
280
|
+
* @returns A new {@link ReducedIterator} containing only the elements that satisfy the condition.
|
|
281
|
+
*/
|
|
282
|
+
public filter<S extends T>(predicate: KeyedTypeGuardPredicate<K, T, S>): ReducedIterator<K, S>;
|
|
42
283
|
public filter(predicate: KeyedIteratee<K, T, boolean>): ReducedIterator<K, T>
|
|
43
284
|
{
|
|
44
285
|
const elements = this._elements.enumerate();
|
|
@@ -51,6 +292,40 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
51
292
|
}
|
|
52
293
|
});
|
|
53
294
|
}
|
|
295
|
+
|
|
296
|
+
/**
|
|
297
|
+
* Maps the elements of the reduced iterator using a given transformation function.
|
|
298
|
+
*
|
|
299
|
+
* This method will iterate over all the elements of the iterator applying the transformation function.
|
|
300
|
+
* The result of the transformation will be included in the new iterator.
|
|
301
|
+
*
|
|
302
|
+
* Since the iterator is lazy, the mapping process will
|
|
303
|
+
* be executed once the resulting iterator is materialized.
|
|
304
|
+
*
|
|
305
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
306
|
+
* This means that the original iterator won't be consumed until the
|
|
307
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
308
|
+
*
|
|
309
|
+
* ---
|
|
310
|
+
*
|
|
311
|
+
* @example
|
|
312
|
+
* ```ts
|
|
313
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
314
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
315
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
316
|
+
* .map((key, value) => value * 2);
|
|
317
|
+
*
|
|
318
|
+
* console.log(results.toObject()); // { odd: 8, even: 32 }
|
|
319
|
+
* ```
|
|
320
|
+
*
|
|
321
|
+
* ---
|
|
322
|
+
*
|
|
323
|
+
* @template V The type of the elements after the transformation.
|
|
324
|
+
*
|
|
325
|
+
* @param iteratee The transformation function to apply to each element of the iterator.
|
|
326
|
+
*
|
|
327
|
+
* @returns A new {@link ReducedIterator} containing the transformed elements.
|
|
328
|
+
*/
|
|
54
329
|
public map<V>(iteratee: KeyedIteratee<K, T, V>): ReducedIterator<K, V>
|
|
55
330
|
{
|
|
56
331
|
const elements = this._elements.enumerate();
|
|
@@ -63,7 +338,74 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
63
338
|
}
|
|
64
339
|
});
|
|
65
340
|
}
|
|
341
|
+
|
|
342
|
+
/**
|
|
343
|
+
* Reduces the elements of the reduced iterator using a given reducer function.
|
|
344
|
+
* This method will consume the entire iterator in the process.
|
|
345
|
+
*
|
|
346
|
+
* It will iterate over all the elements of the iterator applying the reducer function.
|
|
347
|
+
* The result of each iteration will be passed as the accumulator to the next one.
|
|
348
|
+
*
|
|
349
|
+
* The first accumulator value will be the first element of the iterator.
|
|
350
|
+
* The last accumulator value will be the final result of the reduction.
|
|
351
|
+
*
|
|
352
|
+
* Also note that:
|
|
353
|
+
* - If an empty iterator is provided, a {@link ValueException} will be thrown.
|
|
354
|
+
* - If the iterator is infinite, the method will never return.
|
|
355
|
+
*
|
|
356
|
+
* ---
|
|
357
|
+
*
|
|
358
|
+
* @example
|
|
359
|
+
* ```ts
|
|
360
|
+
* const result = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
361
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
362
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
363
|
+
* .reduce((key, accumulator, value) => accumulator + value);
|
|
364
|
+
*
|
|
365
|
+
* console.log(result); // 20
|
|
366
|
+
* ```
|
|
367
|
+
*
|
|
368
|
+
* ---
|
|
369
|
+
*
|
|
370
|
+
* @param reducer The reducer function to apply to the elements of the iterator.
|
|
371
|
+
*
|
|
372
|
+
* @returns The final value after reducing all the elements of the iterator.
|
|
373
|
+
*/
|
|
66
374
|
public reduce(reducer: KeyedReducer<K, T, T>): T;
|
|
375
|
+
|
|
376
|
+
/**
|
|
377
|
+
* Reduces the elements of the reduced iterator using a given reducer function.
|
|
378
|
+
* This method will consume the entire iterator in the process.
|
|
379
|
+
*
|
|
380
|
+
* It will iterate over all the elements of the iterator applying the reducer function.
|
|
381
|
+
* The result of each iteration will be passed as the accumulator to the next one.
|
|
382
|
+
*
|
|
383
|
+
* The first accumulator value will be the provided initial value.
|
|
384
|
+
* The last accumulator value will be the final result of the reduction.
|
|
385
|
+
*
|
|
386
|
+
* If the iterator is infinite, the method will never return.
|
|
387
|
+
*
|
|
388
|
+
* ---
|
|
389
|
+
*
|
|
390
|
+
* @example
|
|
391
|
+
* ```ts
|
|
392
|
+
* const result = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
393
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
394
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
395
|
+
* .reduce((key, { value }, currentValue) => ({ value: value + currentValue }), { value: 0 });
|
|
396
|
+
*
|
|
397
|
+
* console.log(result); // { value: 20 }
|
|
398
|
+
* ```
|
|
399
|
+
*
|
|
400
|
+
* ---
|
|
401
|
+
*
|
|
402
|
+
* @template A The type of the accumulator value which will also be the type of the final result of the reduction.
|
|
403
|
+
*
|
|
404
|
+
* @param reducer The reducer function to apply to the elements of the iterator.
|
|
405
|
+
* @param initialValue The initial value of the accumulator.
|
|
406
|
+
*
|
|
407
|
+
* @returns The final result of the reduction.
|
|
408
|
+
*/
|
|
67
409
|
public reduce<A>(reducer: KeyedReducer<K, T, A>, initialValue: A): A;
|
|
68
410
|
public reduce<A>(reducer: KeyedReducer<K, T, A>, initialValue?: A): A
|
|
69
411
|
{
|
|
@@ -88,7 +430,40 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
88
430
|
return accumulator;
|
|
89
431
|
}
|
|
90
432
|
|
|
91
|
-
|
|
433
|
+
/**
|
|
434
|
+
* Flattens the elements of the reduced iterator using a given transformation function.
|
|
435
|
+
*
|
|
436
|
+
* This method will iterate over all the elements of the iterator applying the transformation function.
|
|
437
|
+
* The result of each transformation will be flattened into the new iterator.
|
|
438
|
+
*
|
|
439
|
+
* Since the iterator is lazy, the flattening process will
|
|
440
|
+
* be executed once the resulting iterator is materialized.
|
|
441
|
+
*
|
|
442
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
443
|
+
* This means that the original iterator won't be consumed until the
|
|
444
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
445
|
+
*
|
|
446
|
+
* ---
|
|
447
|
+
*
|
|
448
|
+
* @example
|
|
449
|
+
* ```ts
|
|
450
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
451
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
452
|
+
* .reduce((key, accumulator, value) => accumulator.concat([value]), () => [])
|
|
453
|
+
* .flatMap((key, value) => value);
|
|
454
|
+
*
|
|
455
|
+
* console.log(results.toObject()); // { odd: [-3, -1, 3, 5], even: [0, 2, 6, 8] }
|
|
456
|
+
* ```
|
|
457
|
+
*
|
|
458
|
+
* ---
|
|
459
|
+
*
|
|
460
|
+
* @template V The type of the elements after the transformation.
|
|
461
|
+
*
|
|
462
|
+
* @param iteratee The transformation function to apply to each element of the iterator.
|
|
463
|
+
*
|
|
464
|
+
* @returns A new {@link AggregatedIterator} containing the flattened elements.
|
|
465
|
+
*/
|
|
466
|
+
public flatMap<V>(iteratee: KeyedIteratee<K, T, V | readonly V[]>): AggregatedIterator<K, V>
|
|
92
467
|
{
|
|
93
468
|
const elements = this._elements.enumerate();
|
|
94
469
|
|
|
@@ -96,11 +471,48 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
96
471
|
{
|
|
97
472
|
for (const [index, [key, element]] of elements)
|
|
98
473
|
{
|
|
99
|
-
|
|
474
|
+
const values = iteratee(key, element, index);
|
|
475
|
+
|
|
476
|
+
if (values instanceof Array)
|
|
477
|
+
{
|
|
478
|
+
for (const value of values) { yield [key, value]; }
|
|
479
|
+
}
|
|
480
|
+
else { yield [key, values]; }
|
|
100
481
|
}
|
|
101
482
|
});
|
|
102
483
|
}
|
|
103
484
|
|
|
485
|
+
/**
|
|
486
|
+
* Drops a given number of elements at the beginning of the reduced iterator.
|
|
487
|
+
* The remaining elements will be included in the new iterator.
|
|
488
|
+
* See also {@link ReducedIterator.take}.
|
|
489
|
+
*
|
|
490
|
+
* Since the iterator is lazy, the dropping process will
|
|
491
|
+
* be executed once the resulting iterator is materialized.
|
|
492
|
+
*
|
|
493
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
494
|
+
* This means that the original iterator won't be consumed until the
|
|
495
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
496
|
+
*
|
|
497
|
+
* Only the dropped elements will be consumed in the process.
|
|
498
|
+
* The rest of the iterator will be consumed once the new iterator is.
|
|
499
|
+
*
|
|
500
|
+
* ---
|
|
501
|
+
*
|
|
502
|
+
* @example
|
|
503
|
+
* ```ts
|
|
504
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
505
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
506
|
+
* .reduce((key, accumulator, value) => accumulator.concat(value), () => [])
|
|
507
|
+
* .drop(1);
|
|
508
|
+
*
|
|
509
|
+
* console.log(results.toObject()); // { even: [0, 2, 6, 8] }
|
|
510
|
+
* ```
|
|
511
|
+
*
|
|
512
|
+
* @param count The number of elements to drop.
|
|
513
|
+
*
|
|
514
|
+
* @returns A new {@link ReducedIterator} containing the remaining elements.
|
|
515
|
+
*/
|
|
104
516
|
public drop(count: number): ReducedIterator<K, T>
|
|
105
517
|
{
|
|
106
518
|
const elements = this._elements.enumerate();
|
|
@@ -113,7 +525,43 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
113
525
|
}
|
|
114
526
|
});
|
|
115
527
|
}
|
|
116
|
-
|
|
528
|
+
|
|
529
|
+
/**
|
|
530
|
+
* Takes a given number of elements at the beginning of the reduced iterator.
|
|
531
|
+
* The elements will be included in the new iterator.
|
|
532
|
+
* See also {@link ReducedIterator.drop}.
|
|
533
|
+
*
|
|
534
|
+
* Since the iterator is lazy, the taking process will
|
|
535
|
+
* be executed once the resulting iterator is materialized.
|
|
536
|
+
*
|
|
537
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
538
|
+
* This means that the original iterator won't be consumed until the
|
|
539
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
540
|
+
*
|
|
541
|
+
* Only the taken elements will be consumed from the original reduced iterator.
|
|
542
|
+
* The rest of the original reduced iterator will be available for further consumption.
|
|
543
|
+
*
|
|
544
|
+
* ---
|
|
545
|
+
*
|
|
546
|
+
* @example
|
|
547
|
+
* ```ts
|
|
548
|
+
* const reduced = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
549
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
550
|
+
* .reduce((key, accumulator, value) => accumulator.concat(value), () => []);
|
|
551
|
+
*
|
|
552
|
+
* const results = iterator.take(1);
|
|
553
|
+
*
|
|
554
|
+
* console.log(results.toObject()); // { odd: [-3, -1, 3, 5] }
|
|
555
|
+
* console.log(reduced.toObject()); // { even: [0, 2, 6, 8] }
|
|
556
|
+
* ```
|
|
557
|
+
*
|
|
558
|
+
* ---
|
|
559
|
+
*
|
|
560
|
+
* @param limit The number of elements to take.
|
|
561
|
+
*
|
|
562
|
+
* @returns A new {@link ReducedIterator} containing the taken elements.
|
|
563
|
+
*/
|
|
564
|
+
public take(limit: number): ReducedIterator<K, T>
|
|
117
565
|
{
|
|
118
566
|
const elements = this._elements.enumerate();
|
|
119
567
|
|
|
@@ -121,17 +569,146 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
121
569
|
{
|
|
122
570
|
for (const [index, [key, element]] of elements)
|
|
123
571
|
{
|
|
124
|
-
if (index >=
|
|
125
|
-
|
|
572
|
+
if (index >= limit) { break; }
|
|
126
573
|
yield [key, element];
|
|
127
574
|
}
|
|
128
575
|
});
|
|
129
576
|
}
|
|
130
577
|
|
|
578
|
+
/**
|
|
579
|
+
* Finds the first element of the reduced iterator that satisfies the given condition.
|
|
580
|
+
*
|
|
581
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
582
|
+
* The first element that satisfies the condition will be returned immediately.
|
|
583
|
+
*
|
|
584
|
+
* Only the elements that are necessary to find the first
|
|
585
|
+
* satisfying one will be consumed from the original iterator.
|
|
586
|
+
* The rest of the iterator will be available for further consumption.
|
|
587
|
+
*
|
|
588
|
+
* Also note that:
|
|
589
|
+
* - If no element satisfies the condition, `undefined` will be returned once the entire iterator is consumed.
|
|
590
|
+
* - If the iterator is infinite and no element satisfies the condition, the method will never return.
|
|
591
|
+
*
|
|
592
|
+
* ---
|
|
593
|
+
*
|
|
594
|
+
* @example
|
|
595
|
+
* ```ts
|
|
596
|
+
* const results = new SmartIterator<number>([-3, -3, -1, 0, 1, 2, 5, 6, 8])
|
|
597
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
598
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
599
|
+
* .find((key, value) => value > 0);
|
|
600
|
+
*
|
|
601
|
+
* console.log(results); // 16
|
|
602
|
+
*
|
|
603
|
+
* @param predicate The condition to check for each element of the iterator.
|
|
604
|
+
*
|
|
605
|
+
* @returns The first element that satisfies the condition, `undefined` otherwise.
|
|
606
|
+
*/
|
|
607
|
+
public find(predicate: KeyedIteratee<K, T, boolean>): T | undefined;
|
|
608
|
+
|
|
609
|
+
/**
|
|
610
|
+
* Finds the first element of the reduced iterator that satisfies the given type guard predicate.
|
|
611
|
+
*
|
|
612
|
+
* This method will iterate over all the elements of the iterator checking if they satisfy the condition.
|
|
613
|
+
* The first element that satisfies the condition will be returned immediately.
|
|
614
|
+
*
|
|
615
|
+
* Only the elements that are necessary to find the first
|
|
616
|
+
* satisfying one will be consumed from the original iterator.
|
|
617
|
+
* The rest of the iterator will be available for further consumption.
|
|
618
|
+
*
|
|
619
|
+
* Also note that:
|
|
620
|
+
* - If no element satisfies the condition, `undefined` will be returned once the entire iterator is consumed.
|
|
621
|
+
* - If the iterator is infinite and no element satisfies the condition, the method will never return.
|
|
622
|
+
*
|
|
623
|
+
* ---
|
|
624
|
+
*
|
|
625
|
+
* @example
|
|
626
|
+
* ```ts
|
|
627
|
+
* const results = new SmartIterator<number | string>(["-3", -3, "-1", 0, 1, 2, "5", 6, 8])
|
|
628
|
+
* .groupBy((value) => Number(value) % 2 === 0 ? "even" : "odd")
|
|
629
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
630
|
+
* .find<number>((key, value) => typeof value === "number");
|
|
631
|
+
*
|
|
632
|
+
* console.log(results); // 16
|
|
633
|
+
*
|
|
634
|
+
* @template S
|
|
635
|
+
* The type of the elements that satisfy the condition.
|
|
636
|
+
* This allows the type-system to infer the correct type of the result.
|
|
637
|
+
*
|
|
638
|
+
* It must be a subtype of the original type of the elements.
|
|
639
|
+
*
|
|
640
|
+
* @param predicate The type guard condition to check for each element of the iterator.
|
|
641
|
+
*
|
|
642
|
+
* @returns The first element that satisfies the condition, `undefined` otherwise.
|
|
643
|
+
*/
|
|
644
|
+
public find<S extends T>(predicate: KeyedTypeGuardPredicate<K, T, S>): S | undefined;
|
|
645
|
+
public find(predicate: KeyedIteratee<K, T, boolean>): T | undefined
|
|
646
|
+
{
|
|
647
|
+
for (const [index, [key, element]] of this._elements.enumerate())
|
|
648
|
+
{
|
|
649
|
+
if (predicate(key, element, index)) { return element; }
|
|
650
|
+
}
|
|
651
|
+
|
|
652
|
+
return undefined;
|
|
653
|
+
}
|
|
654
|
+
|
|
655
|
+
/**
|
|
656
|
+
* Enumerates the elements of the reduced iterator.
|
|
657
|
+
* Each element is paired with its index in a new iterator.
|
|
658
|
+
*
|
|
659
|
+
* Since the iterator is lazy, the enumeration process will
|
|
660
|
+
* be executed once the resulting iterator is materialized.
|
|
661
|
+
*
|
|
662
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
663
|
+
* This means that the original iterator won't be consumed until the
|
|
664
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
665
|
+
*
|
|
666
|
+
* ---
|
|
667
|
+
*
|
|
668
|
+
* @example
|
|
669
|
+
* ```ts
|
|
670
|
+
* const results = new ReducedIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
671
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
672
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
673
|
+
* .enumerate();
|
|
674
|
+
*
|
|
675
|
+
* console.log(results.toObject()); // [[0, 4], [1, 16]]
|
|
676
|
+
* ```
|
|
677
|
+
*
|
|
678
|
+
* ---
|
|
679
|
+
*
|
|
680
|
+
* @returns A new {@link ReducedIterator} object containing the enumerated elements.
|
|
681
|
+
*/
|
|
131
682
|
public enumerate(): ReducedIterator<K, [number, T]>
|
|
132
683
|
{
|
|
133
684
|
return this.map((_, element, index) => [index, element]);
|
|
134
685
|
}
|
|
686
|
+
|
|
687
|
+
/**
|
|
688
|
+
* Removes all duplicate elements from the reduced iterator.
|
|
689
|
+
* The first occurrence of each element will be kept.
|
|
690
|
+
*
|
|
691
|
+
* Since the iterator is lazy, the deduplication process will
|
|
692
|
+
* be executed once the resulting iterator is materialized.
|
|
693
|
+
*
|
|
694
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
695
|
+
* This means that the original iterator won't be consumed until the
|
|
696
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
697
|
+
*
|
|
698
|
+
* ---
|
|
699
|
+
*
|
|
700
|
+
* @example
|
|
701
|
+
* ```ts
|
|
702
|
+
* const results = new ReducedIterator<number>([-3, -1, 0, 2, 3, 6, -3, -1, 1, 5, 6, 8, 7, 2])
|
|
703
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
704
|
+
* .map((key, value) => Math.abs(value))
|
|
705
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
706
|
+
* .unique();
|
|
707
|
+
*
|
|
708
|
+
* console.log(results.toObject()); // { odd: 24 }
|
|
709
|
+
*
|
|
710
|
+
* @returns A new {@link ReducedIterator} containing only the unique elements.
|
|
711
|
+
*/
|
|
135
712
|
public unique(): ReducedIterator<K, T>
|
|
136
713
|
{
|
|
137
714
|
const elements = this._elements;
|
|
@@ -139,7 +716,6 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
139
716
|
return new ReducedIterator(function* ()
|
|
140
717
|
{
|
|
141
718
|
const values = new Set<T>();
|
|
142
|
-
|
|
143
719
|
for (const [key, element] of elements)
|
|
144
720
|
{
|
|
145
721
|
if (values.has(element)) { continue; }
|
|
@@ -150,6 +726,28 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
150
726
|
});
|
|
151
727
|
}
|
|
152
728
|
|
|
729
|
+
/**
|
|
730
|
+
* Counts the number of elements in the reduced iterator.
|
|
731
|
+
* This method will consume the entire iterator in the process.
|
|
732
|
+
*
|
|
733
|
+
* If the iterator is infinite, the method will never return.
|
|
734
|
+
*
|
|
735
|
+
* ---
|
|
736
|
+
*
|
|
737
|
+
* @example
|
|
738
|
+
* ```ts
|
|
739
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
740
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
741
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
742
|
+
* .count();
|
|
743
|
+
*
|
|
744
|
+
* console.log(results); // 2
|
|
745
|
+
* ```
|
|
746
|
+
*
|
|
747
|
+
* ---
|
|
748
|
+
*
|
|
749
|
+
* @returns The number of elements in the iterator.
|
|
750
|
+
*/
|
|
153
751
|
public count(): number
|
|
154
752
|
{
|
|
155
753
|
let index = 0;
|
|
@@ -159,6 +757,31 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
159
757
|
return index;
|
|
160
758
|
}
|
|
161
759
|
|
|
760
|
+
/**
|
|
761
|
+
* Iterates over all elements of the reduced iterator.
|
|
762
|
+
* The elements are passed to the function along with their key and index.
|
|
763
|
+
*
|
|
764
|
+
* This method will consume the entire iterator in the process.
|
|
765
|
+
* If the iterator is infinite, the method will never return.
|
|
766
|
+
*
|
|
767
|
+
* ---
|
|
768
|
+
*
|
|
769
|
+
* @example
|
|
770
|
+
* ```ts
|
|
771
|
+
* const reduced = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
772
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
773
|
+
* .reduce((key, accumulator, value) => accumulator + value);
|
|
774
|
+
*
|
|
775
|
+
* reduced.forEach((key, value, index) =>
|
|
776
|
+
* {
|
|
777
|
+
* console.log(`#${index} - ${key}: ${value}`); // "#0 - odd: 4", "#1 - even: 16"
|
|
778
|
+
* });
|
|
779
|
+
* ```
|
|
780
|
+
*
|
|
781
|
+
* ---
|
|
782
|
+
*
|
|
783
|
+
* @param iteratee The function to apply to each element of the reduced iterator.
|
|
784
|
+
*/
|
|
162
785
|
public forEach(iteratee: KeyedIteratee<K, T>): void
|
|
163
786
|
{
|
|
164
787
|
for (const [index, [key, element]] of this._elements.enumerate())
|
|
@@ -167,6 +790,77 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
167
790
|
}
|
|
168
791
|
}
|
|
169
792
|
|
|
793
|
+
/**
|
|
794
|
+
* Reaggregates the elements of the reduced iterator.
|
|
795
|
+
* The elements are grouped by a new key computed by the given iteratee function.
|
|
796
|
+
*
|
|
797
|
+
* Since the iterator is lazy, the reorganizing process will
|
|
798
|
+
* be executed once the resulting iterator is materialized.
|
|
799
|
+
*
|
|
800
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
801
|
+
* This means that the original iterator won't be consumed until the
|
|
802
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
803
|
+
*
|
|
804
|
+
* ---
|
|
805
|
+
*
|
|
806
|
+
* @example
|
|
807
|
+
* ```ts
|
|
808
|
+
* const results = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, -6, -8])
|
|
809
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
810
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
811
|
+
* .reorganizeBy((key, value) => value > 0 ? "positive" : "negative");
|
|
812
|
+
*
|
|
813
|
+
* console.log(results.toObject()); // { positive: 4, negative: -12 }
|
|
814
|
+
* ```
|
|
815
|
+
*
|
|
816
|
+
* ---
|
|
817
|
+
*
|
|
818
|
+
* @template J The type of the new keys used to group the elements.
|
|
819
|
+
*
|
|
820
|
+
* @param iteratee The function to determine the new key of each element of the iterator.
|
|
821
|
+
*
|
|
822
|
+
* @returns A new {@link AggregatedIterator} containing the elements reorganized by the new keys.
|
|
823
|
+
*/
|
|
824
|
+
public reorganizeBy<J extends PropertyKey>(iteratee: KeyedIteratee<K, T, J>): AggregatedIterator<J, T>
|
|
825
|
+
{
|
|
826
|
+
const elements = this._elements.enumerate();
|
|
827
|
+
|
|
828
|
+
return new AggregatedIterator(function* ()
|
|
829
|
+
{
|
|
830
|
+
for (const [index, [key, element]] of elements)
|
|
831
|
+
{
|
|
832
|
+
yield [iteratee(key, element, index), element];
|
|
833
|
+
}
|
|
834
|
+
});
|
|
835
|
+
}
|
|
836
|
+
|
|
837
|
+
/**
|
|
838
|
+
* An utility method that returns a new {@link SmartIterator}
|
|
839
|
+
* object containing all the keys of the iterator.
|
|
840
|
+
*
|
|
841
|
+
* Since the iterator is lazy, the keys will be extracted
|
|
842
|
+
* be executed once the resulting iterator is materialized.
|
|
843
|
+
*
|
|
844
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
845
|
+
* This means that the original iterator won't be consumed until the
|
|
846
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
847
|
+
*
|
|
848
|
+
* ---
|
|
849
|
+
*
|
|
850
|
+
* @example
|
|
851
|
+
* ```ts
|
|
852
|
+
* const keys = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
853
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
854
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
855
|
+
* .keys();
|
|
856
|
+
*
|
|
857
|
+
* console.log(keys.toArray()); // ["odd", "even"]
|
|
858
|
+
* ```
|
|
859
|
+
*
|
|
860
|
+
* ---
|
|
861
|
+
*
|
|
862
|
+
* @returns A new {@link SmartIterator} containing all the keys of the iterator.
|
|
863
|
+
*/
|
|
170
864
|
public keys(): SmartIterator<K>
|
|
171
865
|
{
|
|
172
866
|
const elements = this._elements;
|
|
@@ -179,10 +873,67 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
179
873
|
}
|
|
180
874
|
});
|
|
181
875
|
}
|
|
182
|
-
|
|
876
|
+
|
|
877
|
+
/**
|
|
878
|
+
* An utility method that returns a new {@link SmartIterator}
|
|
879
|
+
* object containing all the entries of the iterator.
|
|
880
|
+
* Each entry is a tuple containing the key and the element.
|
|
881
|
+
*
|
|
882
|
+
* Since the iterator is lazy, the entries will be extracted
|
|
883
|
+
* be executed once the resulting iterator is materialized.
|
|
884
|
+
*
|
|
885
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
886
|
+
* This means that the original iterator won't be consumed until the
|
|
887
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
888
|
+
*
|
|
889
|
+
* ---
|
|
890
|
+
*
|
|
891
|
+
* @example
|
|
892
|
+
* ```ts
|
|
893
|
+
* const entries = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
894
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
895
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
896
|
+
* .entries();
|
|
897
|
+
*
|
|
898
|
+
* console.log(entries.toArray()); // [["odd", 4], ["even", 16]]
|
|
899
|
+
* ```
|
|
900
|
+
*
|
|
901
|
+
* ---
|
|
902
|
+
*
|
|
903
|
+
* @returns A new {@link SmartIterator} containing all the entries of the iterator.
|
|
904
|
+
*/
|
|
905
|
+
public entries(): SmartIterator<[K, T]>
|
|
183
906
|
{
|
|
184
907
|
return this._elements;
|
|
185
908
|
}
|
|
909
|
+
|
|
910
|
+
/**
|
|
911
|
+
* An utility method that returns a new {@link SmartIterator}
|
|
912
|
+
* object containing all the values of the iterator.
|
|
913
|
+
*
|
|
914
|
+
* Since the iterator is lazy, the values will be extracted
|
|
915
|
+
* be executed once the resulting iterator is materialized.
|
|
916
|
+
*
|
|
917
|
+
* A new iterator will be created, holding the reference to the original one.
|
|
918
|
+
* This means that the original iterator won't be consumed until the
|
|
919
|
+
* new one is and that consuming one of them will consume the other as well.
|
|
920
|
+
*
|
|
921
|
+
* ---
|
|
922
|
+
*
|
|
923
|
+
* @example
|
|
924
|
+
* ```ts
|
|
925
|
+
* const values = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
926
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
927
|
+
* .reduce((key, accumulator, value) => accumulator + value)
|
|
928
|
+
* .values();
|
|
929
|
+
*
|
|
930
|
+
* console.log(values.toArray()); // [4, 16]
|
|
931
|
+
* ```
|
|
932
|
+
*
|
|
933
|
+
* ---
|
|
934
|
+
*
|
|
935
|
+
* @returns A new {@link SmartIterator} containing all the values of the iterator.
|
|
936
|
+
*/
|
|
186
937
|
public values(): SmartIterator<T>
|
|
187
938
|
{
|
|
188
939
|
const elements = this._elements;
|
|
@@ -196,17 +947,82 @@ export default class ReducedIterator<K extends PropertyKey, T>
|
|
|
196
947
|
});
|
|
197
948
|
}
|
|
198
949
|
|
|
950
|
+
/**
|
|
951
|
+
* Materializes the iterator into an array.
|
|
952
|
+
* This method will consume the entire iterator in the process.
|
|
953
|
+
*
|
|
954
|
+
* If the iterator is infinite, the method will never return.
|
|
955
|
+
*
|
|
956
|
+
* ---
|
|
957
|
+
*
|
|
958
|
+
* @example
|
|
959
|
+
* ```ts
|
|
960
|
+
* const reduced = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
961
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
962
|
+
* .reduce((key, accumulator, value) => accumulator + value);
|
|
963
|
+
*
|
|
964
|
+
* console.log(reduced.toArray()); // [4, 16]
|
|
965
|
+
* ```
|
|
966
|
+
*
|
|
967
|
+
* ---
|
|
968
|
+
*
|
|
969
|
+
* @returns The {@link Array} containing all elements of the iterator.
|
|
970
|
+
*/
|
|
199
971
|
public toArray(): T[]
|
|
200
972
|
{
|
|
201
973
|
return Array.from(this.values());
|
|
202
974
|
}
|
|
975
|
+
|
|
976
|
+
/**
|
|
977
|
+
* Materializes the iterator into a map.
|
|
978
|
+
* This method will consume the entire iterator in the process.
|
|
979
|
+
*
|
|
980
|
+
* If the iterator is infinite, the method will never return.
|
|
981
|
+
*
|
|
982
|
+
* ---
|
|
983
|
+
*
|
|
984
|
+
* @example
|
|
985
|
+
* ```ts
|
|
986
|
+
* const reduced = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
987
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
988
|
+
* .reduce((key, accumulator, value) => accumulator + value);
|
|
989
|
+
*
|
|
990
|
+
* console.log(reduced.toMap()); // Map(2) { "odd" => 4, "even" => 16 }
|
|
991
|
+
* ```
|
|
992
|
+
*
|
|
993
|
+
* ---
|
|
994
|
+
*
|
|
995
|
+
* @returns The {@link Map} containing all elements of the iterator.
|
|
996
|
+
*/
|
|
203
997
|
public toMap(): Map<K, T>
|
|
204
998
|
{
|
|
205
|
-
return new Map(this.
|
|
999
|
+
return new Map(this.entries());
|
|
206
1000
|
}
|
|
1001
|
+
|
|
1002
|
+
/**
|
|
1003
|
+
* Materializes the iterator into an object.
|
|
1004
|
+
* This method will consume the entire iterator in the process.
|
|
1005
|
+
*
|
|
1006
|
+
* If the iterator is infinite, the method will never return.
|
|
1007
|
+
*
|
|
1008
|
+
* ---
|
|
1009
|
+
*
|
|
1010
|
+
* @example
|
|
1011
|
+
* ```ts
|
|
1012
|
+
* const reduced = new SmartIterator<number>([-3, -1, 0, 2, 3, 5, 6, 8])
|
|
1013
|
+
* .groupBy((value) => value % 2 === 0 ? "even" : "odd")
|
|
1014
|
+
* .reduce((key, accumulator, value) => accumulator + value);
|
|
1015
|
+
*
|
|
1016
|
+
* console.log(reduced.toObject()); // { odd: 4, even: 16 }
|
|
1017
|
+
* ```
|
|
1018
|
+
*
|
|
1019
|
+
* ---
|
|
1020
|
+
*
|
|
1021
|
+
* @returns The {@link Object} containing all elements of the iterator.
|
|
1022
|
+
*/
|
|
207
1023
|
public toObject(): Record<K, T>
|
|
208
1024
|
{
|
|
209
|
-
return Object.fromEntries(this.
|
|
1025
|
+
return Object.fromEntries(this.entries()) as Record<K, T>;
|
|
210
1026
|
}
|
|
211
1027
|
|
|
212
1028
|
public readonly [Symbol.toStringTag]: string = "ReducedIterator";
|