/*!
 * Copyright (c) Microsoft Corporation and contributors. All rights reserved.
 * Licensed under the MIT License.
 */
import { TreeValue } from "../../../core";
import { EncodedChunkGeneric } from "./formatGeneric";
import { Counter, CounterFilter, DeduplicationTable } from "./chunkCodecUtilities";
/**
 * An identifier which can be compressed using {@link Counter}.
 *
 * @remarks
 * Compression of Identifiers is done after the output is otherwise generated to enable counting all the usages.
 * To avoid having to decode the decode the data array to determine which data is an identifier and which is some other string,
 * some recognizable representation is required.
 * Using a class and checking its prototype works for this, and is why IdentifierToken is a class.
 */
export declare class IdentifierToken {
    readonly identifier: string;
    constructor(identifier: string);
}
/**
 * Format for data emitted during encoding, before dictionary compression of identifiers.
 *
 * @remarks
 * These buffers are mutated after construction if they contain identifiers or shapes.
 */
export declare type BufferFormat<TEncodedShape> = (TreeValue | Shape<TEncodedShape> | IdentifierToken | BufferFormat<TEncodedShape>[])[];
/**
 * Replace shapes and identifiers in buffer and any nested arrays.
 *
 * This looks inside nested arrays (including transitively) but not inside objects.
 *
 * Note that this modifies `buffer` to avoid having to copy it.
 */
export declare function handleShapesAndIdentifiers<TEncodedShape>(version: string, buffer: BufferFormat<TEncodedShape>, identifierFilter?: CounterFilter<string>): EncodedChunkGeneric<TEncodedShape>;
/**
 * A tree shape.
 * This similar to a schema for a tree, though it may be more or less specific than the actual schema system used.
 * Can be encoded into a `TEncodedShape`: when doing so encodes references to shapes (if needed) using {@link Counter}:
 * this can include recursive references (direct or indirect).
 *
 * @remarks
 * Deduplication of shapes is done after the output is otherwise generated (including identifier dictionary encoding).
 * To avoid having to decode the data array to determine which data is a shape and which is some other object,
 * some recognizable representation is required.
 * Using a class and checking its prototype works for this, and is why Shape is a class.
 *
 * Note that deduplication compares shapes by object identity not by content, so encoders must ensure shapes are not duplicated to achieve efficient encoding.
 * Comparison by content would be difficult due to shape containing references to other shapes.
 *
 * @privateRemarks
 * Unlike with identifiers, conversion from the initial form (this class / IdentifierToken) is done by the `encodeShape` method, not by general purpose logic in `handleShapesAndIdentifiers`.
 * For `handleShapesAndIdentifiers` to do the conversion without help from `encodeShape`,
 * instances of this Shape class would have to either be or output an object that is identical to the `TEncodedShape` format except with all shape references as object references instead of indexes.
 * Those objects would have to be deeply traversed looking for shape objects to replace with reference indexes.
 * This is possible, but making it type safe would involve generating derived types from the `TEncodedShape` deeply replacing any shape references, as well as requiring deep traversal of all objects in the encoded output.
 * Such an approach seemed less maintainable and readable than the design taken here which avoids the need for those derived types.
 */
export declare abstract class Shape<TEncodedShape> {
    /**
     * Count this shape's contents.
     *
     * Used to discover referenced shapes (to ensure they are included in the `shapes` passed to `encodeShape`),
     * as well as count usages of shapes and identifiers for more efficient dictionary encoding. See {@link Counter}.
     *
     * @param shapes - must be invoked with each directly referenced shape (which must provided to `encodeShape`).
     * Can be invoked multiple times if a shape is referenced more than once for more efficient dictionary encoding.
     * Should not be invoked with `this` unless this shape references itself.
     */
    abstract count(identifiers: Counter<string>, shapes: (shape: Shape<TEncodedShape>) => void): void;
    /**
     * Produce the final encoded format for this shape.
     *
     * @param identifiers - a subset of identifiers used in this tree, and their corresponding indexes to use for the dictionary encoding.
     * Can be used to encode identifiers referenced by this shape.
     * @param shapes - includes a superset of shapes reported by count.
     * Used to encode references to shapes as numbers.
     */
    abstract encodeShape(identifiers: DeduplicationTable<string>, shapes: DeduplicationTable<Shape<TEncodedShape>>): TEncodedShape;
}
//# sourceMappingURL=chunkEncodingGeneric.d.ts.map