import type { Expressions, TypedExpression, IEnumerable, StrictExpressions, StrictTypedExpression, UnknownExpression } from '../expression.js';
import { BinaryExpression } from '../binary-expression.js';
import { UnaryExpression } from '../unary-expression.js';
import { ParameterExpression } from '../parameter-expression.js';
import { ConstantExpression } from '../constant-expression.js';
import { TypedLambdaExpression } from '../lambda-expression.js';
import { MemberExpression } from '../member-expression.js';
import { CallExpression } from '../call-expression.js';
import { ApplySymbolExpression } from '../apply-symbol-expression.js';
import { NewExpression } from '../new-expression.js';
import type { IVisitable } from '../visitable.js';
import { FormatExpression } from '../../parser.js';
import { TernaryExpression } from '../ternary-expression.js';
import { AssignmentExpression } from '../assignment-expression.js';
/**
 * Defines a comparison function between two values of type T.
 * @template T - The type of values being compared
 */
export type EqualityComparer<T> = (a: T, b: T) => boolean;
/**
 * Base class for implementing the Visitor pattern for expression tree processing.
 */
export declare class ExpressionVisitor {
    /**
     * Processes an assignment expression by visiting its left and right operands.
     * @template T - The expression's value type
     * @param {AssignmentExpression<T>} expression - The assignment expression to process.
     * @returns {AssignmentExpression<Expressions>} The processed assignment expression.
     */
    visitAssign<T extends Expressions = StrictExpressions>(expression: AssignmentExpression<T>): AssignmentExpression<Expressions>;
    /**
     * Visits an expression and returns the processed result.
     * @template T - The type of the expression's output value
     * @param {StrictTypedExpression<T>} expression - A strongly-typed expression
     * @returns {StrictTypedExpression<T>} The processed expression
     */
    visit<T>(expression: StrictTypedExpression<T>): StrictTypedExpression<T>;
    /**
     * Visits a typed expression and returns the processed result.
     * @template T - The type of the expression's output
     * @param {TypedExpression<T>} expression - A typed expression
     * @returns {TypedExpression<T>} The processed expression
     */
    visit<T>(expression: TypedExpression<T>): TypedExpression<T>;
    /**
     * Visits a strict expression and returns the processed result.
     * @param {StrictExpressions} expression - A strict expression node
     * @returns {StrictExpressions} The processed expression
     */
    visit(expression: StrictExpressions): StrictExpressions;
    /**
     * Visits an expression implementing the IVisitable interface.
     * @template T - The visitor type
     * @template U - The return type
     * @param {IVisitable<ExpressionVisitor, U>} expression - A visitable expression
     * @returns {Expressions} The processed expression result
     */
    visit(expression: IVisitable<ExpressionVisitor, any>): Expressions;
    /**
     * Handles unknown expression types by attempting to visit them.
     * @param {UnknownExpression} expression - An unknown expression type
     * @returns {Expressions} The processed expression or throws an error
     */
    visitUnknown(expression: UnknownExpression): Expressions;
    /**
     * Processes a format expression by visiting its components.
     * @template TOutput - The formatted output type
     * @param {FormatExpression<TOutput>} expression - The format expression to process
     * @returns {FormatExpression<TOutput>} The processed format expression
     */
    visitFormat<TOutput>(expression: FormatExpression<TOutput>): FormatExpression<TOutput>;
    /**
     * Processes a new expression by visiting its initialization members.
     * @template T - The expression's value type
     * @param {NewExpression<T>} expression - The new expression to process
     * @returns {StrictExpressions} The processed new expression
     */
    visitNew<T>(expression: NewExpression<T>): StrictExpressions;
    /**
     * Processes an apply symbol expression by visiting its components.
     * @template T - The source expression type
     * @template U - The result type after applying the symbol
     * @param {ApplySymbolExpression<T, U>} expression - The apply symbol expression to process
     * @returns {StrictExpressions} The processed expression
     */
    visitApplySymbol<T, U>(expression: ApplySymbolExpression<T, U>): StrictExpressions;
    /**
     * Processes a call expression by visiting its components.
     * @template T - The source expression type
     * @template TMethod - The method key type
     * @param {CallExpression<T, TMethod>} expression - The call expression to process
     * @returns {StrictExpressions} The processed expression
     */
    visitCall<T, TMethod extends keyof T>(expression: CallExpression<T, TMethod>): StrictExpressions;
    /**
     * Processes a member expression by visiting its components.
     * @template T - The source expression type
     * @template TMember - The member key type
     * @param {MemberExpression<T, TMember, T[TMember]>} expression - The member expression to process
     * @returns {StrictExpressions} The processed expression
     */
    visitMember<T, TMember extends keyof T>(expression: MemberExpression<T, TMember, T[TMember]>): StrictExpressions;
    /**
     * Checks if an expression is a typed expression.
     * @param {Expressions} expression - The expression to check
     * @returns {expression is TypedExpression<T>} Type predicate indicating if the expression is typed
     */
    isTypedExpression<T>(expression: Expressions): expression is TypedExpression<T>;
    /**
     * Processes a lambda expression by visiting its body and parameters.
     * @template T - The lambda's function type
     * @param {TypedLambdaExpression<T>} expression - The lambda expression to process
     * @returns {StrictExpressions} The processed expression
     */
    visitLambda<T extends (...args: unknown[]) => unknown>(expression: TypedLambdaExpression<T>): StrictExpressions;
    /**
     * Default equality comparer for items.
     * @template T - The item type
     * @param {T} a - First item
     * @param {T} b - Second item
     * @returns {boolean} True if items are strictly equal
     */
    private static defaultComparer;
    /**
     * Visits items in an enumerable collection and applies transformation logic.
     * @template T - The item type
     * @template U - The transformed item type
     * @param {IEnumerable<T>} source - Source collection
     * @param {addToNew} addToNew - Callback to add transformed items
     * @param {visitSingle} visitSingle - Transformation function per item
     * @param {EqualityComparer<T>} compare - Optional comparison function
     */
    visitEnumerable<T, U extends T>(source: IEnumerable<T>, addToNew: (item: U, index: number) => void, visitSingle: (item: T, index: number) => U, compare?: EqualityComparer<T>): void;
    /**
     * Visits an array of expressions and applies transformation logic.
     * @template T - The input expression type
     * @template U - The output expression type
     * @param {T[]} expressions - Array of expressions to visit
     * @param {preVisit} preVisit - Optional callback before visiting
     * @returns {U[]} The transformed array of expressions
     */
    visitArray<T extends IVisitable<ExpressionVisitor, U>, U extends T>(expressions: T[], preVisit?: (expression: T, index: number) => void): U[];
    /**
     * Processes a constant expression (no changes required).
     * @param {ConstantExpression<unknown>} expression - The constant expression
     * @returns {StrictExpressions} The same expression
     */
    visitConstant(expression: ConstantExpression<unknown>): StrictExpressions;
    /**
     * Processes a parameter expression (no changes required).
     * @param {ParameterExpression<unknown>} expression - The parameter expression
     * @returns {StrictExpressions} The same expression
     */
    visitParameter(expression: ParameterExpression<unknown>): StrictExpressions;
    /**
     * Processes a unary expression by visiting its operand.
     * @param {UnaryExpression} expression - The unary expression to process
     * @returns {Expressions} The processed unary expression
     */
    visitUnary(expression: UnaryExpression): Expressions;
    /**
     * Processes a binary expression by visiting its left/right operands.
     * @template T - The expression's value type
     * @param {BinaryExpression<T>} expression - The binary expression to process
     * @returns {BinaryExpression<Expressions>} The processed binary expression
     */
    visitBinary<T extends Expressions = StrictExpressions>(expression: BinaryExpression<T>): BinaryExpression<Expressions>;
    /**
     * Processes a ternary expression by visiting its branches.
     * @template T - The expression's value type
     * @param {TernaryExpression<T>} expression - The ternary expression to process
     * @returns {TernaryExpression<Expressions>} The processed ternary expression
     */
    visitTernary<T extends Expressions = StrictExpressions>(expression: TernaryExpression<T>): TernaryExpression<Expressions>;
}
