diff --git a/src/diff/diff.ts b/src/diff/diff.ts index 22dd4d8..a911a05 100644 --- a/src/diff/diff.ts +++ b/src/diff/diff.ts @@ -1,16 +1,16 @@ import bestSubSequence from './lcs'; -export interface DiffData { +export interface DiffData { removed: T[]; - added: T[]; + added: U[]; } -export function diff( +export function diff( a: T[], - b: T[], - compareFunc: (ia: T, ib: T) => boolean = (ia: T, ib: T) => ia === ib, -): DiffData { - const ret: DiffData = { + b: U[], + compareFunc: (ia: T, ib: U) => boolean = (ia: T, ib: U) => ia === (ib as unknown as T), +): DiffData { + const ret: DiffData = { removed: [], added: [], }; diff --git a/src/diff/lcs.ts b/src/diff/lcs.ts index aade358..e3cf928 100644 --- a/src/diff/lcs.ts +++ b/src/diff/lcs.ts @@ -1,4 +1,4 @@ -function lcs(a: T[], b: T[], compareFunc: (a: T, b: T) => boolean): number { +function lcs(a: T[], b: U[], compareFunc: (a: T, b: U) => boolean): number { const M = a.length, N = b.length; const MAX = M + N; @@ -39,23 +39,23 @@ enum Direct { all = horizontal | vertical | diagonal, } -function getSolution( +function getSolution( a: T[], aStart: number, aEnd: number, - b: T[], + b: U[], bStart: number, bEnd: number, d: number, startDirect: Direct, endDirect: Direct, - compareFunc: (a: T, b: T) => boolean, + compareFunc: (a: T, b: U) => boolean, elementsChanged: ( type: 'add' | 'remove' | 'same', a: T[], aStart: number, aEnd: number, - b: T[], + b: U[], bStart: number, bEnd: number, ) => void, @@ -285,16 +285,16 @@ function getSolution( ); } -export default function bestSubSequence( +export default function bestSubSequence( a: T[], - b: T[], - compareFunc: (a: T, b: T) => boolean, + b: U[], + compareFunc: (a: T, b: U) => boolean, elementsChanged: ( type: 'add' | 'remove' | 'same', a: T[], aStart: number, aEnd: number, - b: T[], + b: U[], bStart: number, bEnd: number, ) => void, diff --git a/src/diff/same.ts b/src/diff/same.ts index 79f1005..1422765 100644 --- a/src/diff/same.ts +++ b/src/diff/same.ts @@ -1,9 +1,9 @@ import bestSubSequence from './lcs'; -export default function ( +export default function ( a: T[], - b: T[], - compareFunc: (ia: T, ib: T) => boolean = (ia: T, ib: T) => ia === ib, + b: U[], + compareFunc: (ia: T, ib: U) => boolean = (ia: T, ib: U) => ia === (ib as unknown as T), ): T[] { const ret: T[] = []; bestSubSequence(a, b, compareFunc, (type, oldArr, oldStart, oldEnd) => { diff --git a/src/index.ts b/src/index.ts index 454ec68..b72c6f4 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,5 +1,6 @@ +import bestSubSequence from './diff/lcs'; import same from './diff/same'; -export { same }; +export { bestSubSequence, same }; export * from './diff/diff'; diff --git a/src/test/diff.spec.ts b/src/test/diff.spec.ts index f71a098..2735fa0 100644 --- a/src/test/diff.spec.ts +++ b/src/test/diff.spec.ts @@ -63,4 +63,16 @@ describe('Diff', () => { '', ); }); + + it('Functional test on arrays of different types', () => { + assert.deepStrictEqual( + diff.diff([1, 2, 3], ['2', '3', '4'], (l, r) => { + assert.equal(typeof l, 'number'); + assert.equal(typeof r, 'string'); + + return l.toString() === r; + }), + { added: ['4'], removed: [1] }, + ); + }); }); diff --git a/src/test/index.spec.ts b/src/test/index.spec.ts index a8d50f4..9e694c8 100644 --- a/src/test/index.spec.ts +++ b/src/test/index.spec.ts @@ -9,6 +9,41 @@ describe('Index', () => { assert.deepStrictEqual(diff.same([1, 2, 3], [2, 3, 4]), [2, 3]); }); + it('bestSubSequence function in index', () => { + const changes: ( + | { type: 'same' | 'remove'; values: number[] } + | { type: 'add'; values: string[] } + )[] = []; + + diff.bestSubSequence( + [1, 2, 3], + ['2', '3', '4'], + (l, r) => { + assert.equal(typeof l, 'number'); + assert.equal(typeof r, 'string'); + + return l.toString() === r; + }, + (type, a, aStart, aEnd, b, bStart, bEnd) => { + assert.equal(typeof a[0], 'number'); + assert.equal(typeof b[0], 'string'); + + if (type === 'add') { + changes.push({ type, values: b.slice(bStart, bEnd) }); + } else { + changes.push({ type, values: a.slice(aStart, aEnd) }); + } + }, + ); + + assert.deepStrictEqual(changes, [ + { type: 'remove', values: [1] }, + { type: 'same', values: [2] }, + { type: 'same', values: [3] }, + { type: 'add', values: ['4'] }, + ]); + }); + it('diff data and function in index', () => { const result: diff.DiffData = { added: [1, 2], diff --git a/src/test/same.spec.ts b/src/test/same.spec.ts index 2baaa6f..a47bdac 100644 --- a/src/test/same.spec.ts +++ b/src/test/same.spec.ts @@ -144,4 +144,16 @@ describe('Same', () => { ]; assert.deepStrictEqual(same(a, b, compare), result); }); + + it('Functional test on arrays of different types', () => { + assert.deepStrictEqual( + same([1, 2, 3], ['2', '3', '4'], (l, r) => { + assert.equal(typeof l, 'number'); + assert.equal(typeof r, 'string'); + + return l.toString() === r; + }), + [2, 3], + ); + }); });