mirror of
https://github.com/dolthub/dolt.git
synced 2026-04-28 12:40:16 -05:00
sequences return a compare func used for diffs (#1771)
This commit is contained in:
@@ -17,6 +17,7 @@ import Ref from './ref.js';
|
||||
import SequenceChunker from './sequence-chunker.js';
|
||||
import type {BoundaryChecker, makeChunkFn} from './sequence-chunker.js';
|
||||
import {Kind} from './noms-kind.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
|
||||
export default class Blob extends Collection<IndexedSequence> {
|
||||
constructor(bytes: Uint8Array) {
|
||||
@@ -134,6 +135,11 @@ export class BlobLeafSequence extends IndexedSequence<number> {
|
||||
getOffset(idx: number): number {
|
||||
return idx;
|
||||
}
|
||||
|
||||
getCompareFn(other: IndexedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
this.items[idx] === other.items[otherIdx];
|
||||
}
|
||||
}
|
||||
|
||||
const blobWindowSize = 64;
|
||||
|
||||
@@ -7,7 +7,6 @@
|
||||
import type {Splice} from './edit-distance.js';
|
||||
import {calcSplices, SPLICE_ADDED, SPLICE_AT, SPLICE_FROM,
|
||||
SPLICE_REMOVED} from './edit-distance.js';
|
||||
import {equals} from './compare.js';
|
||||
import {IndexedMetaSequence} from './meta-sequence.js';
|
||||
import {invariant} from './assert.js';
|
||||
import type {IndexedSequence} from './indexed-sequence.js';
|
||||
@@ -50,9 +49,7 @@ export function diff(last: IndexedSequence, lastHeight: number, lastOffset: numb
|
||||
invariant(last.isMeta === current.isMeta);
|
||||
invariant(lastHeight === currentHeight);
|
||||
|
||||
const splices = calcSplices(last.length, current.length, last.isMeta ?
|
||||
(l, c) => equals(last.items[l].ref, current.items[c].ref) :
|
||||
(l, c) => equals(last.items[l], current.items[c]));
|
||||
const splices = calcSplices(last.length, current.length, last.getCompareFn(current));
|
||||
|
||||
const splicesP = splices.map(splice => {
|
||||
if (!last.isMeta || splice[SPLICE_REMOVED] === 0 || splice[SPLICE_ADDED] === 0) {
|
||||
|
||||
@@ -8,12 +8,20 @@ import {AsyncIterator} from './async-iterator.js';
|
||||
import type {AsyncIteratorResult} from './async-iterator.js';
|
||||
import {notNull} from './assert.js';
|
||||
import Sequence, {search, SequenceCursor} from './sequence.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
import {equals} from './compare.js';
|
||||
|
||||
export class IndexedSequence<T> extends Sequence<T> {
|
||||
getOffset(idx: number): number { // eslint-disable-line no-unused-vars
|
||||
throw new Error('override');
|
||||
}
|
||||
|
||||
getCompareFn(other: IndexedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
// $FlowIssue
|
||||
equals(this.items[idx], other.items[otherIdx]);
|
||||
}
|
||||
|
||||
async newCursorAt(idx: number): Promise<IndexedSequenceCursor> {
|
||||
let cursor: ?IndexedSequenceCursor = null;
|
||||
let sequence: ?IndexedSequence = this;
|
||||
|
||||
+5
-3
@@ -23,6 +23,7 @@ import {OrderedSequence, OrderedSequenceCursor, OrderedSequenceIterator} from
|
||||
import diff from './ordered-sequence-diff.js';
|
||||
import {ValueBase} from './value.js';
|
||||
import {Kind} from './noms-kind.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
|
||||
export type MapEntry<K: Value, V: Value> = [K, V];
|
||||
|
||||
@@ -196,9 +197,10 @@ export class MapLeafSequence<K: Value, V: Value> extends
|
||||
return this.items[idx][KEY];
|
||||
}
|
||||
|
||||
equalsAt(idx: number, other: MapEntry<K, V>): boolean {
|
||||
const entry = this.items[idx];
|
||||
return equals(entry[KEY], other[KEY]) && equals(entry[VALUE], other[VALUE]);
|
||||
getCompareFn(other: OrderedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
equals(this.items[idx][KEY], other.items[otherIdx][KEY]) &&
|
||||
equals(this.items[idx][VALUE], other.items[otherIdx][VALUE]);
|
||||
}
|
||||
|
||||
get chunks(): Array<Ref> {
|
||||
|
||||
@@ -23,7 +23,7 @@ import List from './list.js';
|
||||
import Map from './map.js';
|
||||
import Set from './set.js';
|
||||
import Blob from './blob.js';
|
||||
import {equals} from './compare.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
|
||||
export type MetaSequence = Sequence<MetaTuple>;
|
||||
|
||||
@@ -145,6 +145,11 @@ export class IndexedMetaSequence extends IndexedSequence<MetaTuple<number>> {
|
||||
getOffset(idx: number): number {
|
||||
return this._offsets[idx] - 1;
|
||||
}
|
||||
|
||||
getCompareFn(other: IndexedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
this.items[idx].ref.targetHash.equals(other.items[otherIdx].ref.targetHash);
|
||||
}
|
||||
}
|
||||
|
||||
export function newMapMetaSequence<K: Value>(vr: ?ValueReader,
|
||||
@@ -194,8 +199,9 @@ export class OrderedMetaSequence<K: Value> extends OrderedSequence<K, MetaTuple<
|
||||
return this.items[idx].value;
|
||||
}
|
||||
|
||||
equalsAt(idx: number, other: MetaTuple): boolean {
|
||||
return equals(this.items[idx].ref, other.ref);
|
||||
getCompareFn(other: OrderedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
this.items[idx].ref.targetHash.equals(other.items[otherIdx].ref.targetHash);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ export default async function diff<K: Value, T>(
|
||||
await fastForward(lastCur, currentCur);
|
||||
|
||||
while (lastCur.valid && currentCur.valid &&
|
||||
!lastCur.sequence.equalsAt(lastCur.idx, currentCur.getCurrent())) {
|
||||
!lastCur.sequence.getCompareFn(currentCur.sequence)(lastCur.idx, currentCur.idx)) {
|
||||
const lastKey = lastCur.getCurrentKey(), currentKey = currentCur.getCurrentKey();
|
||||
|
||||
if (equals(lastKey, currentKey)) {
|
||||
@@ -109,5 +109,5 @@ async function doFastForward(allowPastEnd: boolean,
|
||||
}
|
||||
|
||||
function isCurrentEqual(a: SequenceCursor, b: SequenceCursor): boolean {
|
||||
return a.sequence.equalsAt(a.idx, b.getCurrent());
|
||||
return a.sequence.getCompareFn(b.sequence)(a.idx, b.idx);
|
||||
}
|
||||
|
||||
@@ -10,6 +10,7 @@ import type Value from './value.js'; // eslint-disable-line no-unused-vars
|
||||
import {invariant, notNull} from './assert.js';
|
||||
import {compare} from './compare.js';
|
||||
import search from './binary-search.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
import Sequence, {SequenceCursor} from './sequence.js';
|
||||
import {ValueBase} from './value.js';
|
||||
|
||||
@@ -47,10 +48,7 @@ export class OrderedSequence<K: Value, T> extends Sequence<T> {
|
||||
throw new Error('override');
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the item in this sequence at |idx| is equal to |other|.
|
||||
*/
|
||||
equalsAt(idx: number, other: any): boolean { // eslint-disable-line no-unused-vars
|
||||
getCompareFn(other: OrderedSequence): EqualsFn { // eslint-disable-line no-unused-vars
|
||||
throw new Error('override');
|
||||
}
|
||||
}
|
||||
|
||||
+4
-2
@@ -26,6 +26,7 @@ import {sha1Size} from './hash.js';
|
||||
import {removeDuplicateFromOrdered} from './map.js';
|
||||
import {getValueChunks} from './sequence.js';
|
||||
import {Kind} from './noms-kind.js';
|
||||
import type {EqualsFn} from './edit-distance.js';
|
||||
|
||||
const setWindowSize = 1;
|
||||
const setPattern = ((1 << 6) | 0) - 1;
|
||||
@@ -201,8 +202,9 @@ export class SetLeafSequence<K: Value> extends OrderedSequence<K, K> {
|
||||
return this.items[idx];
|
||||
}
|
||||
|
||||
equalsAt(idx: number, other: any): boolean {
|
||||
return equals(this.items[idx], other);
|
||||
getCompareFn(other: OrderedSequence): EqualsFn {
|
||||
return (idx: number, otherIdx: number) =>
|
||||
equals(this.items[idx], other.items[otherIdx]);
|
||||
}
|
||||
|
||||
get chunks(): Array<Ref> {
|
||||
|
||||
Reference in New Issue
Block a user