import { writeLiteralToCellStore } from '../../engine-value-utils.js';
import { makeCellEntity } from '../../entity-ids.js';
import { addEngineCounter } from '../../perf/engine-counters.js';
import { markBatchApplied } from '../../replica-state.js';
import { directScalarLiteralNumericValue } from './direct-scalar-helpers.js';
import { PendingNumericCellValues } from './direct-formula-index-collection.js';
import { exactLookupBatchOldNumeric, exactLookupBatchWriteHandled, prepareExactLookupBatchSkipPlan, } from './operation-exact-lookup-batch-skip-plan.js';
import { reverseUint32ArrayInPlace, tagTrustedPhysicalTrackedChanges } from './operation-change-helpers.js';
import { emitCellMutationFastPathBatchResult } from './operation-fast-path-batch-result.js';
import { createOperationDirectAggregateRectangularBatchFastPath } from './operation-direct-aggregate-rectangular-batch-fast-path.js';
import { createOperationFreshRectangularLiteralBatchFastPath } from './operation-fresh-rectangular-literal-batch-fast-path.js';
import { DirectScalarPhysicalSliceTracker } from './operation-direct-scalar-physical-slice-tracker.js';
import { createOperationDirectScalarRowPairBatchFastPaths } from './operation-direct-scalar-row-pair-batch-fast-paths.js';
import { createOperationDirectScalarSingleColumnBatchFastPaths } from './operation-direct-scalar-single-column-batch-fast-paths.js';
import { writeOperationNumericLiteralToExistingCellWithoutColumnNotify } from './operation-literal-write-helpers.js';
const EMPTY_CHANGED_CELLS = new Uint32Array(0);
export function createOperationDirectScalarBatchFastPaths(args) {
    const { emitBatch, hasTrackedExactLookupDependents, hasTrackedSortedLookupDependents, hasTrackedDirectRangeDependents, canFastPathLiteralOverwrite, canUseDirectFormulaPostRecalc, canSkipFormulaColumnVersion, directScalarCellNumericValue, writeNumericLiteralToCellStore, applyTerminalDirectFormulaNumericResult, applyDirectFormulaNumericResult, applyDirectFormulaCurrentResult, tryEvaluateDirectScalarWithPendingNumbers, tryEvaluateDirectScalarNumericWithPendingNumbers, planExactLookupNumericColumnWrite, planApproximateLookupNumericColumnWrite, } = args;
    const { tryApplyDenseSingleColumnAffineDirectScalarLiteralBatch, tryApplyDenseSingleColumnDirectScalarLiteralBatch, tryApplyDenseSingleColumnAffineExistingNumericBatch, } = createOperationDirectScalarSingleColumnBatchFastPaths(args);
    const { tryApplyDenseRowPairSimpleDirectScalarLiteralBatch, tryApplyDenseRowPairDirectScalarLiteralBatch, tryApplyDenseRowPairExistingNumericBatch, } = createOperationDirectScalarRowPairBatchFastPaths({
        state: args.state,
        emitBatch,
        hasTrackedExactLookupDependents,
        hasTrackedSortedLookupDependents,
        hasTrackedDirectRangeDependents,
        canFastPathLiteralOverwrite,
        canUseDirectFormulaPostRecalc,
        canSkipFormulaColumnVersion,
        applyTerminalDirectFormulaNumericResults: args.applyTerminalDirectFormulaNumericResults,
        getEntityDependents: args.getEntityDependents,
        materializeDeferredStructuralFormulaSources: args.materializeDeferredStructuralFormulaSources,
        beginMutationCollection: args.beginMutationCollection,
        ensureRecalcScratchCapacity: args.ensureRecalcScratchCapacity,
        resetMaterializedCellScratch: args.resetMaterializedCellScratch,
        getBatchMutationDepth: args.getBatchMutationDepth,
        setBatchMutationDepth: args.setBatchMutationDepth,
        markInputChanged: args.markInputChanged,
        markExplicitChanged: args.markExplicitChanged,
        getChangedInputBuffer: args.getChangedInputBuffer,
        deferKernelSync: args.deferKernelSync,
        composeDisjointEventChanges: args.composeDisjointEventChanges,
        captureChangedCells: args.captureChangedCells,
    });
    const tryApplyExistingNumericDirectScalarBatch = (record, batch) => tryApplyDenseSingleColumnAffineExistingNumericBatch(record, batch) || tryApplyDenseRowPairExistingNumericBatch(record, batch);
    let directAggregateRectangularBatchFastPath;
    const getDirectAggregateRectangularBatchFastPath = () => (directAggregateRectangularBatchFastPath ??= createOperationDirectAggregateRectangularBatchFastPath({
        state: args.state,
        emitBatch,
        hasTrackedExactLookupDependents,
        hasTrackedSortedLookupDependents,
        canFastPathLiteralOverwrite,
        canUseDirectFormulaPostRecalc,
        canSkipFormulaColumnVersion,
        writeNumericLiteralToCellStore,
        applyTerminalDirectFormulaNumericResult,
        getSingleEntityDependent: args.getSingleEntityDependent,
        materializeDeferredStructuralFormulaSources: args.materializeDeferredStructuralFormulaSources,
        beginMutationCollection: args.beginMutationCollection,
        ensureRecalcScratchCapacity: args.ensureRecalcScratchCapacity,
        resetMaterializedCellScratch: args.resetMaterializedCellScratch,
        getBatchMutationDepth: args.getBatchMutationDepth,
        setBatchMutationDepth: args.setBatchMutationDepth,
        markInputChanged: args.markInputChanged,
        markExplicitChanged: args.markExplicitChanged,
        getChangedInputBuffer: args.getChangedInputBuffer,
        deferKernelSync: args.deferKernelSync,
        composeDisjointEventChanges: args.composeDisjointEventChanges,
        captureChangedCells: args.captureChangedCells,
    }));
    const tryApplyDenseRectangularDirectAggregateLiteralBatch = (...input) => getDirectAggregateRectangularBatchFastPath().tryApplyDenseRectangularDirectAggregateLiteralBatch(...input);
    let freshRectangularLiteralBatchFastPath;
    const getFreshRectangularLiteralBatchFastPath = () => (freshRectangularLiteralBatchFastPath ??= createOperationFreshRectangularLiteralBatchFastPath({
        state: args.state,
        emitBatch,
        hasTrackedExactLookupDependents,
        hasTrackedSortedLookupDependents,
        writeNumericLiteralToCellStore,
        materializeDeferredStructuralFormulaSources: args.materializeDeferredStructuralFormulaSources,
        beginMutationCollection: args.beginMutationCollection,
        ensureRecalcScratchCapacity: args.ensureRecalcScratchCapacity,
        resetMaterializedCellScratch: args.resetMaterializedCellScratch,
        getBatchMutationDepth: args.getBatchMutationDepth,
        setBatchMutationDepth: args.setBatchMutationDepth,
        markInputChanged: args.markInputChanged,
        markExplicitChanged: args.markExplicitChanged,
        getChangedInputBuffer: args.getChangedInputBuffer,
        deferKernelSync: args.deferKernelSync,
        captureChangedCells: args.captureChangedCells,
    }));
    const tryApplyFreshDenseRectangularNumericLiteralBatch = (...input) => getFreshRectangularLiteralBatchFastPath().tryApplyFreshDenseRectangularNumericLiteralBatch(...input);
    const tryApplyLookupOnlyNumericColumnLiteralBatch = (refs, batch, potentialNewCells) => {
        const firstRef = refs[0];
        if (firstRef === undefined || refs.length < 32) {
            return false;
        }
        const firstMutation = firstRef.mutation;
        if (firstMutation.kind !== 'setCellValue' || typeof firstMutation.value !== 'number' || Object.is(firstMutation.value, -0)) {
            return false;
        }
        const sheet = args.state.workbook.getSheetById(firstRef.sheetId);
        if (!sheet || sheet.structureVersion !== 1 || hasTrackedDirectRangeDependents(firstRef.sheetId, firstMutation.col)) {
            return false;
        }
        const hasExactLookupDependents = hasTrackedExactLookupDependents(firstRef.sheetId, firstMutation.col);
        const hasSortedLookupDependents = hasTrackedSortedLookupDependents(firstRef.sheetId, firstMutation.col);
        if (!hasExactLookupDependents && !hasSortedLookupDependents) {
            return false;
        }
        const exactSkipPlan = hasExactLookupDependents
            ? prepareExactLookupBatchSkipPlan({
                col: firstMutation.col,
                formulas: args.state.formulas,
                getEntityDependents: args.getEntityDependents,
                getSingleEntityDependent: args.getSingleEntityDependent,
                readNumericValue: directScalarCellNumericValue,
                sheetId: firstRef.sheetId,
            })
            : { kind: 'all' };
        const inputCellIndices = new Uint32Array(refs.length);
        const cellStore = args.state.workbook.cellStore;
        let ascending = true;
        let descending = true;
        let previousRow = -1;
        for (let refIndex = 0; refIndex < refs.length; refIndex += 1) {
            const ref = refs[refIndex];
            const mutation = ref.mutation;
            if (ref.sheetId !== firstRef.sheetId ||
                mutation.kind !== 'setCellValue' ||
                mutation.col !== firstMutation.col ||
                typeof mutation.value !== 'number' ||
                Object.is(mutation.value, -0)) {
                return false;
            }
            if (refIndex > 0) {
                ascending &&= mutation.row > previousRow;
                descending &&= mutation.row < previousRow;
            }
            previousRow = mutation.row;
            const existingIndex = ref.cellIndex !== undefined &&
                cellStore.sheetIds[ref.cellIndex] === ref.sheetId &&
                cellStore.rows[ref.cellIndex] === mutation.row &&
                cellStore.cols[ref.cellIndex] === mutation.col
                ? ref.cellIndex
                : sheet.grid.getPhysical(mutation.row, mutation.col);
            if (existingIndex === -1 || !canFastPathLiteralOverwrite(existingIndex)) {
                return false;
            }
            const plannedOldNumber = exactLookupBatchOldNumeric(exactSkipPlan, mutation.row);
            const oldNumber = plannedOldNumber !== undefined && !hasSortedLookupDependents ? plannedOldNumber : directScalarCellNumericValue(existingIndex);
            if (oldNumber === undefined) {
                return false;
            }
            if (!(exactLookupBatchWriteHandled(exactSkipPlan, mutation.row, oldNumber, mutation.value) ||
                (exactSkipPlan.kind === 'fallback' &&
                    planExactLookupNumericColumnWrite(firstRef.sheetId, firstMutation.col, mutation.row, oldNumber, mutation.value).handled))) {
                return false;
            }
            if (hasSortedLookupDependents &&
                !planApproximateLookupNumericColumnWrite(firstRef.sheetId, sheet.name, firstMutation.col, mutation.row, oldNumber, mutation.value)
                    .handled) {
                return false;
            }
            inputCellIndices[refIndex] = existingIndex;
        }
        if (!ascending && !descending) {
            return false;
        }
        const hasGeneralEventListeners = args.state.events.hasListeners();
        const hasTrackedEventListeners = args.state.events.hasTrackedListeners();
        const hasWatchedCellListeners = args.state.events.hasCellListeners();
        const requiresChangedSet = hasGeneralEventListeners || hasTrackedEventListeners || hasWatchedCellListeners;
        if (!hasGeneralEventListeners && !hasWatchedCellListeners && (potentialNewCells ?? 0) === 0) {
            args.materializeDeferredStructuralFormulaSources();
            args.setBatchMutationDepth(args.getBatchMutationDepth() + 1);
            try {
                for (let index = 0; index < refs.length; index += 1) {
                    const mutation = refs[index].mutation;
                    if (mutation.kind !== 'setCellValue' || typeof mutation.value !== 'number') {
                        throw new Error('Invalid numeric column batch mutation');
                    }
                    writeOperationNumericLiteralToExistingCellWithoutColumnNotify({
                        cellStore: args.state.workbook.cellStore,
                        cellIndex: inputCellIndices[index],
                        value: mutation.value,
                    });
                }
                args.state.workbook.notifyColumnWritten(firstRef.sheetId, firstMutation.col);
            }
            finally {
                args.setBatchMutationDepth(args.getBatchMutationDepth() - 1);
            }
            if (hasExactLookupDependents) {
                args.invalidateExactLookupColumn({ sheetName: sheet.name, col: firstMutation.col });
            }
            if (hasSortedLookupDependents) {
                args.invalidateSortedLookupColumn({ sheetName: sheet.name, col: firstMutation.col });
            }
            if (batch) {
                markBatchApplied(args.state.replicaState, batch);
            }
            const changed = hasTrackedEventListeners
                ? ascending
                    ? inputCellIndices
                    : reverseUint32ArrayInPlace(inputCellIndices)
                : EMPTY_CHANGED_CELLS;
            args.deferKernelSync(hasTrackedEventListeners ? changed : inputCellIndices);
            addEngineCounter(args.state.counters, 'kernelSyncOnlyRecalcSkips');
            emitCellMutationFastPathBatchResult({
                state: args.state,
                changed,
                changedInputCount: refs.length,
                explicitChangedCount: hasTrackedEventListeners ? refs.length : 0,
                hasGeneralEventListeners,
                hasTrackedEventListeners,
                hasWatchedCellListeners,
                captureChangedCells: args.captureChangedCells,
                batch,
                emitBatch,
            });
            return true;
        }
        args.materializeDeferredStructuralFormulaSources();
        args.beginMutationCollection();
        const reservedNewCells = potentialNewCells ?? 0;
        args.state.workbook.cellStore.ensureCapacity(args.state.workbook.cellStore.size + reservedNewCells);
        args.ensureRecalcScratchCapacity(args.state.workbook.cellStore.size + refs.length + 1);
        args.resetMaterializedCellScratch(reservedNewCells);
        let changedInputCount = 0;
        let explicitChangedCount = 0;
        args.setBatchMutationDepth(args.getBatchMutationDepth() + 1);
        try {
            for (let index = 0; index < refs.length; index += 1) {
                const cellIndex = inputCellIndices[index];
                const mutation = refs[index].mutation;
                if (mutation.kind !== 'setCellValue' || typeof mutation.value !== 'number') {
                    throw new Error('Invalid numeric column batch mutation');
                }
                writeOperationNumericLiteralToExistingCellWithoutColumnNotify({
                    cellStore: args.state.workbook.cellStore,
                    cellIndex,
                    value: mutation.value,
                });
                changedInputCount = args.markInputChanged(cellIndex, changedInputCount);
                if (requiresChangedSet) {
                    explicitChangedCount = args.markExplicitChanged(cellIndex, explicitChangedCount);
                }
            }
            args.state.workbook.notifyColumnWritten(firstRef.sheetId, firstMutation.col);
        }
        finally {
            args.setBatchMutationDepth(args.getBatchMutationDepth() - 1);
        }
        if (hasExactLookupDependents) {
            args.invalidateExactLookupColumn({ sheetName: sheet.name, col: firstMutation.col });
        }
        if (hasSortedLookupDependents) {
            args.invalidateSortedLookupColumn({ sheetName: sheet.name, col: firstMutation.col });
        }
        if (batch) {
            markBatchApplied(args.state.replicaState, batch);
        }
        const changedInputArray = args.getChangedInputBuffer().subarray(0, changedInputCount);
        args.deferKernelSync(changedInputArray);
        const changed = requiresChangedSet ? (ascending ? inputCellIndices : reverseUint32ArrayInPlace(inputCellIndices)) : EMPTY_CHANGED_CELLS;
        addEngineCounter(args.state.counters, 'kernelSyncOnlyRecalcSkips');
        emitCellMutationFastPathBatchResult({
            state: args.state,
            changed,
            changedInputCount,
            explicitChangedCount,
            hasGeneralEventListeners,
            hasTrackedEventListeners,
            hasWatchedCellListeners,
            captureChangedCells: args.captureChangedCells,
            batch,
            emitBatch,
        });
        return true;
    };
    const tryApplyCoalescedDirectScalarLiteralBatch = (refs, batch, source, potentialNewCells) => {
        if (source === 'restore' ||
            (source !== 'local' && batch !== null) ||
            refs.length < 32 ||
            args.state.formulas.size === 0 ||
            args.state.workbook.hasPivots()) {
            return false;
        }
        if (args.hasVolatileFormulas?.()) {
            return false;
        }
        if (tryApplyLookupOnlyNumericColumnLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyFreshDenseRectangularNumericLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyDenseRectangularDirectAggregateLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyDenseSingleColumnAffineDirectScalarLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyDenseSingleColumnDirectScalarLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyDenseRowPairSimpleDirectScalarLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        if (tryApplyDenseRowPairDirectScalarLiteralBatch(refs, batch, potentialNewCells)) {
            return true;
        }
        const pendingNumbers = new PendingNumericCellValues();
        const inputCellIndices = [];
        const inputNumericValues = new Float64Array(refs.length);
        const formulaCellIndices = [];
        const formulaSeen = new Set();
        let canUseNumericInputWrites = true;
        const physicalSliceTracker = new DirectScalarPhysicalSliceTracker();
        const trackedColumnDependencyFlagsBySheet = new Map();
        const hasTrackedColumnDependencies = (sheetId, col) => {
            let flagsByColumn = trackedColumnDependencyFlagsBySheet.get(sheetId);
            if (flagsByColumn === undefined) {
                flagsByColumn = new Map();
                trackedColumnDependencyFlagsBySheet.set(sheetId, flagsByColumn);
            }
            const cached = flagsByColumn.get(col);
            if (cached !== undefined) {
                return cached;
            }
            const hasDependencies = hasTrackedExactLookupDependents(sheetId, col) ||
                hasTrackedSortedLookupDependents(sheetId, col) ||
                hasTrackedDirectRangeDependents(sheetId, col);
            flagsByColumn.set(col, hasDependencies);
            return hasDependencies;
        };
        for (let refIndex = 0; refIndex < refs.length; refIndex += 1) {
            const ref = refs[refIndex];
            const mutation = ref.mutation;
            if (mutation.kind !== 'setCellValue') {
                return false;
            }
            if (typeof mutation.value !== 'number' || Object.is(mutation.value, -0)) {
                canUseNumericInputWrites = false;
            }
            const nextNumber = directScalarLiteralNumericValue(mutation.value);
            if (nextNumber === undefined) {
                return false;
            }
            inputNumericValues[refIndex] = nextNumber;
            const sheet = args.state.workbook.getSheetById(ref.sheetId);
            if (!sheet || sheet.structureVersion !== 1) {
                return false;
            }
            const candidate = ref.cellIndex;
            const existingIndex = candidate !== undefined &&
                args.state.workbook.cellStore.sheetIds[candidate] === ref.sheetId &&
                args.state.workbook.cellStore.rows[candidate] === mutation.row &&
                args.state.workbook.cellStore.cols[candidate] === mutation.col
                ? candidate
                : sheet.grid.getPhysical(mutation.row, mutation.col);
            if (existingIndex === -1 || !canFastPathLiteralOverwrite(existingIndex) || pendingNumbers.has(existingIndex)) {
                return false;
            }
            physicalSliceTracker.noteCell(ref.sheetId, mutation.row, mutation.col, 'input');
            if (hasTrackedColumnDependencies(ref.sheetId, mutation.col)) {
                return false;
            }
            const dependents = args.getEntityDependents(makeCellEntity(existingIndex));
            for (let dependentIndex = 0; dependentIndex < dependents.length; dependentIndex += 1) {
                const formulaCellIndex = dependents[dependentIndex];
                const formula = args.state.formulas.get(formulaCellIndex);
                if (!formula ||
                    formula.directScalar === undefined ||
                    !canUseDirectFormulaPostRecalc(formulaCellIndex) ||
                    ((args.state.workbook.cellStore.flags[formulaCellIndex] ?? 0) & 8 /* CellFlags.InCycle */) !== 0) {
                    return false;
                }
                if (!formulaSeen.has(formulaCellIndex)) {
                    formulaSeen.add(formulaCellIndex);
                    formulaCellIndices.push(formulaCellIndex);
                    const cellStore = args.state.workbook.cellStore;
                    const formulaSheetId = cellStore.sheetIds[formulaCellIndex];
                    const formulaSheet = formulaSheetId === undefined ? undefined : args.state.workbook.getSheetById(formulaSheetId);
                    if (formulaSheetId === undefined || (formulaSheet && formulaSheet.structureVersion !== 1)) {
                        physicalSliceTracker.markUntrusted();
                    }
                    else {
                        physicalSliceTracker.noteCell(formulaSheetId, cellStore.rows[formulaCellIndex] ?? 0, cellStore.cols[formulaCellIndex] ?? 0, 'formula');
                    }
                }
            }
            pendingNumbers.set(existingIndex, nextNumber);
            inputCellIndices.push(existingIndex);
        }
        if (inputCellIndices.length === 0 || formulaCellIndices.length === 0) {
            return false;
        }
        const formulaNumericResults = new Float64Array(formulaCellIndices.length);
        let canUseNumericFormulaResults = true;
        for (let index = 0; index < formulaCellIndices.length; index += 1) {
            const formula = args.state.formulas.get(formulaCellIndices[index]);
            const result = formula?.directScalar
                ? tryEvaluateDirectScalarNumericWithPendingNumbers(formula.directScalar, pendingNumbers)
                : undefined;
            if (result === undefined) {
                canUseNumericFormulaResults = false;
                break;
            }
            formulaNumericResults[index] = result;
        }
        let formulaResults;
        if (!canUseNumericFormulaResults) {
            const evaluatedFormulaResults = [];
            for (let index = 0; index < formulaCellIndices.length; index += 1) {
                const formula = args.state.formulas.get(formulaCellIndices[index]);
                const result = formula?.directScalar ? tryEvaluateDirectScalarWithPendingNumbers(formula.directScalar, pendingNumbers) : undefined;
                if (result === undefined) {
                    return false;
                }
                evaluatedFormulaResults[index] = result;
            }
            formulaResults = evaluatedFormulaResults;
        }
        args.materializeDeferredStructuralFormulaSources();
        args.beginMutationCollection();
        const reservedNewCells = potentialNewCells ?? 0;
        args.state.workbook.cellStore.ensureCapacity(args.state.workbook.cellStore.size + reservedNewCells);
        args.ensureRecalcScratchCapacity(args.state.workbook.cellStore.size + formulaCellIndices.length + refs.length + 1);
        args.resetMaterializedCellScratch(reservedNewCells);
        const hasGeneralEventListeners = args.state.events.hasListeners();
        const hasTrackedEventListeners = args.state.events.hasTrackedListeners();
        const hasWatchedCellListeners = args.state.events.hasCellListeners();
        const requiresChangedSet = hasGeneralEventListeners || hasTrackedEventListeners || hasWatchedCellListeners;
        let changedInputCount = 0;
        let explicitChangedCount = 0;
        args.setBatchMutationDepth(args.getBatchMutationDepth() + 1);
        try {
            args.state.workbook.withBatchedColumnVersionUpdates(() => {
                for (let index = 0; index < refs.length; index += 1) {
                    const cellIndex = inputCellIndices[index];
                    if (canUseNumericInputWrites) {
                        writeNumericLiteralToCellStore(cellIndex, inputNumericValues[index]);
                    }
                    else {
                        const mutation = refs[index].mutation;
                        if (mutation.kind !== 'setCellValue') {
                            throw new Error('Expected coalesced direct scalar batch to contain only literal writes');
                        }
                        writeLiteralToCellStore(args.state.workbook.cellStore, cellIndex, mutation.value, args.state.strings);
                    }
                    args.state.workbook.notifyCellValueWritten(cellIndex);
                    changedInputCount = args.markInputChanged(cellIndex, changedInputCount);
                    if (requiresChangedSet) {
                        explicitChangedCount = args.markExplicitChanged(cellIndex, explicitChangedCount);
                    }
                }
            });
        }
        finally {
            args.setBatchMutationDepth(args.getBatchMutationDepth() - 1);
        }
        if (batch) {
            markBatchApplied(args.state.replicaState, batch);
        }
        const changedInputArray = args.getChangedInputBuffer().subarray(0, changedInputCount);
        args.deferKernelSync(changedInputArray);
        const formulaChanged = requiresChangedSet ? new Uint32Array(formulaCellIndices.length) : EMPTY_CHANGED_CELLS;
        args.state.workbook.withBatchedColumnVersionUpdates(() => {
            for (let index = 0; index < formulaCellIndices.length; index += 1) {
                const cellIndex = formulaCellIndices[index];
                if (canUseNumericFormulaResults) {
                    applyDirectFormulaNumericResult(cellIndex, formulaNumericResults[index]);
                }
                else if (!applyDirectFormulaCurrentResult(cellIndex, formulaResults[index])) {
                    throw new Error('Failed to apply direct scalar batch result');
                }
                if (requiresChangedSet) {
                    formulaChanged[index] = cellIndex;
                }
            }
        });
        addEngineCounter(args.state.counters, 'directScalarDeltaApplications', formulaCellIndices.length);
        addEngineCounter(args.state.counters, 'directScalarDeltaOnlyRecalcSkips');
        const changed = requiresChangedSet ? args.composeDisjointEventChanges(formulaChanged, explicitChangedCount) : EMPTY_CHANGED_CELLS;
        const trustedPhysicalSheetId = hasTrackedEventListeners
            ? physicalSliceTracker.getTrustedSheetIdForTrackedChanges(explicitChangedCount, changed.length)
            : undefined;
        if (requiresChangedSet && trustedPhysicalSheetId !== undefined) {
            tagTrustedPhysicalTrackedChanges(changed, trustedPhysicalSheetId, explicitChangedCount);
        }
        emitCellMutationFastPathBatchResult({
            state: args.state,
            changed,
            changedInputCount,
            explicitChangedCount,
            hasGeneralEventListeners,
            hasTrackedEventListeners,
            hasWatchedCellListeners,
            captureChangedCells: args.captureChangedCells,
            batch,
            emitBatch,
        });
        return true;
    };
    return {
        tryApplyCoalescedDirectScalarLiteralBatch,
        tryApplyDenseRowPairDirectScalarLiteralBatch,
        tryApplyLookupOnlyNumericColumnLiteralBatch,
        tryApplyDenseRectangularDirectAggregateLiteralBatch,
        tryApplyFreshDenseRectangularNumericLiteralBatch,
        tryApplyDenseSingleColumnAffineExistingNumericBatch,
        tryApplyExistingNumericDirectScalarBatch,
    };
}
//# sourceMappingURL=operation-direct-scalar-batch-fast-paths.js.map