sync
This commit is contained in:
292
src/equality-map/impl.ts
Normal file
292
src/equality-map/impl.ts
Normal file
@@ -0,0 +1,292 @@
|
||||
import { asEqualityComparer } from "../equality-comparer/sync.js";
|
||||
import { EqualityComparer, EqualityComparisonOrComparer, MaybeAsyncEqualityComparison } from "../equality-comparer/types.js";
|
||||
import { MaybeAsyncIterable } from "../types.js";
|
||||
import { AsyncEqualityMap, EqualityMap, EqualityMapEntry } from "./types.js";
|
||||
|
||||
export class NativeEqualityMap<K, V> implements EqualityMap<K, V> {
|
||||
readonly #map = new Map<K, V>();
|
||||
|
||||
get size() {
|
||||
return this.#map.size;
|
||||
}
|
||||
|
||||
get(key: K) {
|
||||
return this.#map.get(key);
|
||||
}
|
||||
|
||||
set(key: K, value: V) {
|
||||
const existing = this.get(key);
|
||||
this.#map.set(key, value);
|
||||
return existing;
|
||||
}
|
||||
|
||||
setAll(entries: Iterable<EqualityMapEntry<K, V>>) {
|
||||
for (const [key, value] of entries) {
|
||||
this.set(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
contains(key: K) {
|
||||
return this.#map.has(key);
|
||||
}
|
||||
|
||||
remove(key: K) {
|
||||
const existing = this.get(key);
|
||||
this.#map.delete(key);
|
||||
return existing;
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.#map.clear();
|
||||
}
|
||||
|
||||
keys() {
|
||||
return this.#map.keys();
|
||||
}
|
||||
|
||||
values() {
|
||||
return this.#map.values();
|
||||
}
|
||||
|
||||
entries() {
|
||||
return this.#map.entries();
|
||||
}
|
||||
|
||||
[Symbol.iterator]() {
|
||||
return this.#map[Symbol.iterator]();
|
||||
}
|
||||
}
|
||||
|
||||
export class CustomEqualityMap<K, V> implements EqualityMap<K, V> {
|
||||
readonly #list: EqualityMapEntry<K, V>[] = [];
|
||||
readonly #keyComparer: EqualityComparer<K>;
|
||||
|
||||
constructor(keyComparer: EqualityComparisonOrComparer<K>) {
|
||||
this.#keyComparer = asEqualityComparer(keyComparer);
|
||||
}
|
||||
|
||||
get size() {
|
||||
return this.#list.length;
|
||||
}
|
||||
|
||||
get(key: K) {
|
||||
for (const entry of this.#list) {
|
||||
if (this.#keyComparer.equals(key, entry[0])) {
|
||||
return entry[1];
|
||||
}
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
set(key: K, value: V) {
|
||||
for (const entry of this.#list) {
|
||||
if (this.#keyComparer.equals(key, entry[0])) {
|
||||
const previous = entry[1];
|
||||
entry[1] = value;
|
||||
return previous;
|
||||
}
|
||||
}
|
||||
|
||||
this.#list.push([key, value]);
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
setAll(entries: Iterable<EqualityMapEntry<K, V>>) {
|
||||
for (const [key, value] of entries) {
|
||||
this.set(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
contains(key: K) {
|
||||
for (const entry of this.#list) {
|
||||
if (this.#keyComparer.equals(key, entry[0])) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
remove(key: K) {
|
||||
for (let i = 0; i < this.#list.length; i++) {
|
||||
if (this.#keyComparer.equals(key, this.#list[i][0])) {
|
||||
const removed = this.#list.splice(i, 1);
|
||||
return removed[0][1];
|
||||
}
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.#list.length = 0;
|
||||
}
|
||||
|
||||
*keys() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry[0];
|
||||
}
|
||||
}
|
||||
|
||||
*values() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry[1];
|
||||
}
|
||||
}
|
||||
|
||||
entries() {
|
||||
return this[Symbol.iterator]();
|
||||
}
|
||||
|
||||
*[Symbol.iterator]() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry.slice() as EqualityMapEntry<K, V>; // no entry mutation allowed!
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export class NativeAsyncEqualityMap<K, V> implements AsyncEqualityMap<K, V> {
|
||||
readonly #map = new Map<K, V>();
|
||||
|
||||
get size() {
|
||||
return this.#map.size;
|
||||
}
|
||||
|
||||
async get(key: K) {
|
||||
return this.#map.get(key);
|
||||
}
|
||||
|
||||
async set(key: K, value: V) {
|
||||
const existing = await this.get(key);
|
||||
this.#map.set(key, value);
|
||||
return existing;
|
||||
}
|
||||
|
||||
async setAll(entries: MaybeAsyncIterable<EqualityMapEntry<K, V>>) {
|
||||
for await (const [key, value] of entries) {
|
||||
await this.set(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
async contains(key: K) {
|
||||
return this.#map.has(key);
|
||||
}
|
||||
|
||||
async remove(key: K) {
|
||||
const existing = await this.get(key);
|
||||
this.#map.delete(key);
|
||||
return existing;
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.#map.clear();
|
||||
}
|
||||
|
||||
keys() {
|
||||
return this.#map.keys();
|
||||
}
|
||||
|
||||
values() {
|
||||
return this.#map.values();
|
||||
}
|
||||
|
||||
entries() {
|
||||
return this.#map.entries();
|
||||
}
|
||||
|
||||
[Symbol.iterator]() {
|
||||
return this.#map[Symbol.iterator]();
|
||||
}
|
||||
}
|
||||
|
||||
export class CustomAsyncEqualityMap<K, V> implements AsyncEqualityMap<K, V> {
|
||||
readonly #list: EqualityMapEntry<K, V>[] = [];
|
||||
readonly #keyComparer: MaybeAsyncEqualityComparison<K>;
|
||||
|
||||
constructor(keyComparer: MaybeAsyncEqualityComparison<K>) {
|
||||
this.#keyComparer = keyComparer;
|
||||
}
|
||||
|
||||
get size() {
|
||||
return this.#list.length;
|
||||
}
|
||||
|
||||
async get(key: K) {
|
||||
for (const entry of this.#list) {
|
||||
if (await this.#keyComparer(key, entry[0])) {
|
||||
return entry[1];
|
||||
}
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
async set(key: K, value: V) {
|
||||
for (const entry of this.#list) {
|
||||
if (await this.#keyComparer(key, entry[0])) {
|
||||
const previous = entry[1];
|
||||
entry[1] = value;
|
||||
return previous;
|
||||
}
|
||||
}
|
||||
|
||||
this.#list.push([key, value]);
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
async setAll(entries: MaybeAsyncIterable<EqualityMapEntry<K, V>>) {
|
||||
for await (const [key, value] of entries) {
|
||||
await this.set(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
async contains(key: K) {
|
||||
for (const entry of this.#list) {
|
||||
if (await this.#keyComparer(key, entry[0])) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
async remove(key: K) {
|
||||
for (let i = 0; i < this.#list.length; i++) {
|
||||
if (await this.#keyComparer(key, this.#list[i][0])) {
|
||||
const removed = this.#list.splice(i, 1);
|
||||
return removed[0][1];
|
||||
}
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
|
||||
clear() {
|
||||
this.#list.length = 0;
|
||||
}
|
||||
|
||||
*keys() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry[0];
|
||||
}
|
||||
}
|
||||
|
||||
*values() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry[1];
|
||||
}
|
||||
}
|
||||
|
||||
entries() {
|
||||
return this[Symbol.iterator]();
|
||||
}
|
||||
|
||||
*[Symbol.iterator]() {
|
||||
for (const entry of this.#list) {
|
||||
yield entry.slice() as EqualityMapEntry<K, V>; // no entry mutation allowed!
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user