@tynq/core v0.0.12
TYNQ - TypeScript-Integrated Query
TYNQ is a port of C# LINQ to compose enumerable sequences using the existing iterator pattern.
TYNQ defines a standard way to interact with any sequence of elements that implements an iterator. Native types that are iterable are patched by importing from the index file @tync/core
. Custom types can be patched by using the patchAsEnumerable
.
Install TYNQ from npm
npm install @tynq/core
IEnumerator<T>
Defines a standardized way of iterating over a sequence of elements. An Enumerator also implements Iterable<T>
, meaning that it can be used by existing elements of the language like for of
or the spread ...
operator.
Create an enumerator from an existing iterator
import { Enumerator } from '@tynq/core';
const source = [1, 2, 3];
const enumerator = new Enumerator(source);
while (enumerator.moveNext()) {
console.log(enumerator.current);
// 1
// 2
// 3
}
IEnumerable<T>
Exposes a generic set of methods that can be used to enumerate a sequence of elements. An IEnumerable<T>
only needs to implement a single method, getEnumerator
that returns the enumerator for the sequence. Because of language limitations, IEnumerable<T>
is an abstract class that needs to be extended when creating a custom type that implements IEnumerable<T>
. All native elements are already patched to implement the interface when the package is imported.
import "@tynq/core";
// Using arrays
const source = [1, 2, 3];
const first = source.first(); // 1
const where = source
.where((e) => e > 1)
.where((e) => e < 3)
.single(); // 2
// Using map
const source = [
{ username: "Michael", id: 1 }
{ username: "Matt", id: 2 },
{ username: "Ian", id: 3 }
]
const users = source
.where((e) => e.id > 1)
.toMap((e) => e.id, (e) => e.username)
.skip(1)
.count(); // 1
Implementing IEnumerable<T>
In order to implement IEnumerable<T>
, the type needs to extend the base IEnumerable<T>
class, and implement the getEnumerator
method.
import { Enumerator, IEnumerable } from '@tynq/core';
export interface IList<T> extends IEnumerable<[TKey, TValue]> {
add(item: T): void;
clear(): void;
}
export class List<T> extends IEnumerable<T> implements IList<T> {
private _list: T[] = [];
public getEnumerator(): IEnumerator<T> {
const listIterator = function* () {
for (const element of this._list) {
yield element;
}
};
return new Enumerator(listIterator);
}
public add(item: T): void {
this._list.push(item);
}
public clear(): void {
this._list.length = 0;
}
}
Using custom IEnumerable<T>
import { List } from './list';
const list = new List<number>();
list.add(1);
list.add(2);
list.add(3);
list.count(); // 3
list.sum(); // 6
list.clear();
list.count(); // 0
list.any(); // false