import { Eq, OptLazy, TraverseState, type ArrayNonEmpty, type CollectFun, type ToJSON } from '@rimbu/common';
import { Reducer, Transformer, type FastIterator, type Stream, type StreamSource } from '@rimbu/stream';
import { type StreamConstructors } from '@rimbu/stream/custom';
/**
 * A reusable base implementation for `Stream` that provides all high-level operations
 * in terms of a `FastIterator` returned from `[Symbol.iterator]`.
 *
 * Custom stream implementations in `@rimbu/stream/custom` extend this class.
 * @typeparam T - the element type
 */
export declare abstract class StreamBase<T> implements Stream<T> {
    abstract [Symbol.iterator](): FastIterator<T>;
    stream(): this;
    equals(other: StreamSource<T>, { eq, negate }?: {
        eq?: Eq<T>;
        negate?: boolean;
    }): boolean;
    assumeNonEmpty(): Stream.NonEmpty<T>;
    asNormal(): Stream<T>;
    prepend(value: OptLazy<T>): Stream.NonEmpty<T>;
    append(value: OptLazy<T>): Stream.NonEmpty<T>;
    forEach(f: (value: T, index: number, halt: () => void) => void, options?: {
        state?: TraverseState;
    }): void;
    forEachPure<A extends readonly unknown[]>(f: (value: T, ...args: A) => void, ...args: A): void;
    indexed(options?: {
        startIndex?: number;
    }): Stream<[number, T]>;
    filter(pred: (value: T, index: number, halt: () => void) => boolean, options?: {
        negate?: boolean | undefined;
    }): any;
    filterPure<A extends readonly unknown[]>(options: {
        pred: (value: T, ...args: A) => boolean;
        negate?: boolean | undefined;
    }, ...args: A): any;
    withOnly<F extends T>(values: F[]): Stream<F>;
    without<F extends T>(values: F[]): any;
    map<T2>(mapFun: (value: T, index: number) => T2): Stream<T2>;
    mapPure<T2, A extends readonly unknown[]>(mapFun: (value: T, ...args: A) => T2, ...args: A): Stream<T2>;
    collect<R>(collectFun: CollectFun<T, R>): Stream<R>;
    flatMap<T2>(flatMapFun: (value: T, index: number, halt: () => void) => StreamSource<T2>): Stream<T2>;
    flatZip<T2>(flatMapFun: (value: T, index: number, halt: () => void) => StreamSource<T2>): Stream<[T, T2]>;
    transform<R>(transformer: Transformer<T, R>): Stream<R>;
    first<O>(otherwise?: OptLazy<O>): T | O;
    last<O>(otherwise?: OptLazy<O>): T | O;
    single<O>(otherwise?: OptLazy<O>): T | O;
    count(): number;
    countElement(value: T, options?: {
        eq?: Eq<T>;
        negate?: boolean;
    }): number;
    find<O>(pred: (value: T, index: number) => boolean, options?: {
        occurrance?: number | undefined;
        negate?: boolean | undefined;
        otherwise?: OptLazy<O>;
    }): T | O;
    elementAt<O>(index: number, otherwise?: OptLazy<O>): T | O;
    indicesWhere(pred: (value: T) => boolean, options?: {
        negate?: boolean;
    }): Stream<number>;
    indicesOf(searchValue: T, options?: {
        eq?: Eq<T>;
        negate?: boolean;
    }): Stream<number>;
    indexWhere(pred: (value: T, index: number) => boolean, options?: {
        occurrance?: number;
        negate?: boolean;
    }): number | undefined;
    indexOf(searchValue: T, options?: {
        occurrance?: number | undefined;
        eq?: Eq<T> | undefined;
        negate?: boolean | undefined;
    }): number | undefined;
    some(pred: (value: T, index: number) => boolean, options?: {
        negate?: boolean;
    }): boolean;
    every(pred: (value: T, index: number) => boolean, options?: {
        negate?: boolean;
    }): boolean;
    contains(searchValue: T, options?: {
        amount?: number;
        eq?: Eq<T>;
        negate?: boolean;
    }): boolean;
    containsSlice(source: StreamSource.NonEmpty<T>, options?: {
        eq?: Eq<T>;
        amount?: number;
    }): boolean;
    takeWhile(pred: (value: T, index: number) => boolean, options?: {
        negate?: boolean;
    }): Stream<T>;
    dropWhile(pred: (value: T, index: number) => boolean, options?: {
        negate?: boolean;
    }): Stream<T>;
    take(amount: number): Stream<T>;
    drop(amount: number): Stream<T>;
    repeat(amount?: number): Stream<T>;
    concat(...others: ArrayNonEmpty<StreamSource<T>>): Stream.NonEmpty<T>;
    min<O>(otherwise?: OptLazy<O>): T | O;
    minBy<O>(compare: (v1: T, v2: T) => number, otherwise?: OptLazy<O>): T | O;
    max<O>(otherwise?: OptLazy<O>): T | O;
    maxBy<O>(compare: (v1: T, v2: T) => number, otherwise?: OptLazy<O>): T | O;
    intersperse(sep: StreamSource<T>): Stream<T>;
    join({ sep, start, end, valueToString, ifEmpty, }?: {
        sep?: string | undefined;
        start?: string | undefined;
        end?: string | undefined;
        valueToString?: StringConstructor | undefined;
        ifEmpty?: undefined;
    }): string;
    mkGroup({ sep, start, end, }?: {
        sep?: StreamSource<T>;
        start?: StreamSource<T>;
        end?: StreamSource<T>;
    }): any;
    splitWhere<R>(pred: (value: T, index: number) => boolean, options?: {
        negate?: boolean | undefined;
        collector?: Reducer<T, R> | undefined;
    }): Stream<R>;
    splitOn<R>(sepElem: T, options?: {
        eq?: Eq<T> | undefined;
        negate?: boolean | undefined;
        collector?: Reducer<T, R> | undefined;
    }): Stream<R>;
    splitOnSlice<R>(sepSeq: StreamSource<T>, options?: {
        eq?: Eq<T> | undefined;
        collector?: Reducer<T, R> | undefined;
    }): Stream<R>;
    distinctPrevious(options?: {
        eq?: Eq<T>;
        negate?: boolean;
    }): Stream<T>;
    window<R>(windowSize: number, options?: {
        skipAmount?: number | undefined;
        collector?: Reducer<T, R> | undefined;
    }): Stream<R>;
    partition(pred: (value: T, index: number) => any, options?: {
        collectorTrue?: any;
        collectorFalse?: any;
    }): [any, any];
    groupBy<K, R>(valueToKey: (value: T, index: number) => K, options?: {
        collector?: Reducer<readonly [K, T], R> | undefined;
    }): R;
    fold<R>(init: OptLazy<R>, next: (current: R, value: T, index: number, halt: () => void) => R): R;
    foldStream<R>(init: OptLazy<R>, next: (current: R, value: T, index: number, halt: () => void) => R): Stream<R>;
    reduce<const S extends Reducer.CombineShape<T2>, T2 extends T = T>(shape: S & Reducer.CombineShape<T2>): Reducer.CombineResult<S>;
    reduceStream<const S extends Reducer.CombineShape<T2>, T2 extends T = T>(shape: S & Reducer.CombineShape<T2>): Stream<Reducer.CombineResult<S>>;
    toArray(): T[];
    toString(): string;
    toJSON(): ToJSON<T[], 'Stream'>;
}
/**
 * Converts any `StreamSource` into a concrete `Stream` implementation.
 * @typeparam T - the element type
 * @param source - the source to convert
 */
export declare const fromStreamSource: {
    <T>(source: StreamSource.NonEmpty<T>): Stream.NonEmpty<T>;
    <T>(source: StreamSource<T>): Stream<T>;
};
/**
 * Returns true if the given `source` StreamSource is known to be empty.
 * @param source - a StreamSource
 * @note
 * If this function returns false, it does not guarantee that the Stream is not empty. It only
 * means that it is not known if it is empty.
 */
/**
 * Returns true if the given `source` is a `StreamSource` that is known to be empty.
 * If this function returns `false`, the source may still be empty; it is simply not known.
 * @param source - a potential stream source
 */
export declare function isEmptyStreamSourceInstance(source: StreamSource<any>): boolean;
declare const streamSourceHelpers: {
    fromStreamSource: {
        <T>(source: StreamSource.NonEmpty<T>): Stream.NonEmpty<T>;
        <T>(source: StreamSource<T>): Stream<T>;
    };
    isEmptyStreamSourceInstance: typeof isEmptyStreamSourceInstance;
};
export type StreamSourceHelpers = typeof streamSourceHelpers;
/**
 * Default implementation of the `StreamConstructors` interface.
 * This instance backs the exported `Stream` value.
 */
export declare const StreamConstructorsImpl: StreamConstructors;
export {};
