UNPKG

@electric-sql/d2mini

Version:

D2Mini is a minimal implementation of Differential Dataflow for performing in-memory incremental view maintenance.

62 lines (61 loc) 3.08 kB
import { KeyValue, PipedOperator } from '../types.js'; import { DifferenceStreamReader, DifferenceStreamWriter, UnaryOperator } from '../graph.js'; export interface TopKWithFractionalIndexOptions { limit?: number; offset?: number; } export type TopKChanges<V> = { /** Indicates which element moves into the topK (if any) */ moveIn: IndexedValue<V> | null; /** Indicates which element moves out of the topK (if any) */ moveOut: IndexedValue<V> | null; }; /** * A topK data structure that supports insertions and deletions * and returns changes to the topK. */ export interface TopK<V> { insert(value: V): TopKChanges<V>; delete(value: V): TopKChanges<V>; } /** * Operator for fractional indexed topK operations * This operator maintains fractional indices for sorted elements * and only updates indices when elements move position */ export declare class TopKWithFractionalIndexOperator<K, V1> extends UnaryOperator<[ K, V1 ], [ K, IndexedValue<V1> ]> { #private; constructor(id: number, inputA: DifferenceStreamReader<[K, V1]>, output: DifferenceStreamWriter<[K, [V1, string]]>, comparator: (a: V1, b: V1) => number, options: TopKWithFractionalIndexOptions); protected createTopK(offset: number, limit: number, comparator: (a: TaggedValue<V1>, b: TaggedValue<V1>) => number): TopK<TaggedValue<V1>>; run(): void; processElement(key: K, value: V1, multiplicity: number, result: Array<[[K, [V1, string]], number]>): void; } /** * Limits the number of results based on a comparator, with optional offset. * This works on a keyed stream, where the key is the first element of the tuple. * The ordering is within a key group, i.e. elements are sorted within a key group * and the limit + offset is applied to that sorted group. * To order the entire stream, key by the same value for all elements such as null. * * Uses fractional indexing to minimize the number of changes when elements move positions. * Each element is assigned a fractional index that is lexicographically sortable. * When elements move, only the indices of the moved elements are updated, not all elements. * * @param comparator - A function that compares two elements * @param options - An optional object containing limit and offset properties * @returns A piped operator that orders the elements and limits the number of results */ export declare function topKWithFractionalIndex<K extends T extends KeyValue<infer K, infer _V> ? K : never, V1 extends T extends KeyValue<K, infer V> ? V : never, T>(comparator: (a: V1, b: V1) => number, options?: TopKWithFractionalIndexOptions): PipedOperator<T, KeyValue<K, [V1, string]>>; export type FractionalIndex = string; export type IndexedValue<V> = [V, FractionalIndex]; export declare function indexedValue<V>(value: V, index: FractionalIndex): IndexedValue<V>; export declare function getValue<V>(indexedValue: IndexedValue<V>): V; export declare function getIndex<V>(indexedValue: IndexedValue<V>): FractionalIndex; export type Tag = number; export type TaggedValue<V> = [V, Tag];