Skip to content
Snippets Groups Projects
Commit 5b6a6915 authored by David Sehnal's avatar David Sehnal
Browse files

tuples

parent fbd7c35f
No related branches found
No related tags found
No related merge requests found
......@@ -10,7 +10,7 @@ import { hash2 } from './hash-functions'
* Represents a pair of two integers as a double,
* Caution: === does not work, because of NaN, use IntTuple.areEqual for equality
*/
interface IntTuple extends Number { }
interface IntTuple { '@type': 'int-tuple' }
namespace IntTuple {
export interface Unpacked { fst: number, snd: number }
......@@ -36,17 +36,17 @@ namespace IntTuple {
export function pack(fst: number, snd: number): IntTuple {
_int32[0] = fst;
_int32[1] = snd;
return _float64[0];
return _float64[0] as any;
}
export function pack1(t: Unpacked): IntTuple {
_int32[0] = t.fst;
_int32[1] = t.snd;
return _float64[0];
return _float64[0] as any;
}
export function unpack(t: IntTuple, target: Unpacked): Unpacked {
_float64[0] = t as number;
_float64[0] = t as any;
target.fst = _int32[0];
target.snd = _int32[1];
return target;
......@@ -57,40 +57,40 @@ namespace IntTuple {
}
export function fst(t: IntTuple): number {
_float64[0] = t as number;
_float64[0] = t as any;
return _int32[0];
}
export function snd(t: IntTuple): number {
_float64[0] = t as number;
_float64[0] = t as any;
return _int32[1];
}
/** Normal equality does not work, because NaN === NaN ~> false */
export function areEqual(a: IntTuple, b: IntTuple) {
_float64[0] = a as number;
_float64_1[0] = b as number;
_float64[0] = a as any;
_float64_1[0] = b as any;
return _int32[0] === _int32_1[0] && _int32[1] === _int32_1[1];
}
export function compare(a: IntTuple, b: IntTuple) {
_float64[0] = a as number;
_float64_1[0] = b as number;
_float64[0] = a as any;
_float64_1[0] = b as any;
const x = _int32[0] - _int32_1[0];
if (x !== 0) return x;
return _int32[1] - _int32_1[1];
}
export function compareInArray(xs: ArrayLike<IntTuple>, i: number, j: number) {
_float64[0] = xs[i] as number;
_float64_1[0] = xs[j] as number;
_float64[0] = xs[i] as any;
_float64_1[0] = xs[j] as any;
const x = _int32[0] - _int32_1[0];
if (x !== 0) return x;
return _int32[1] - _int32_1[1];
}
export function hashCode(t: IntTuple) {
_float64[0] = t as number;
_float64[0] = t as any;
return hash2(_int32[0], _int32[1]);
}
}
......
......@@ -210,7 +210,7 @@ function valuesI(set: MultiSetImpl): Iterator<IntTuple.Unpacked> {
return new ElementsIterator(set as MultiSetElements);
}
function isArrayLike(x: any): x is ArrayLike<number> {
function isArrayLike(x: any): x is ArrayLike<IntTuple> {
return x && (typeof x.length === 'number' && (x instanceof Array || !!x.buffer));
}
......@@ -321,10 +321,10 @@ function getOffsetIndex(xs: ArrayLike<number>, value: number) {
return value < xs[min] ? min - 1 : min;
}
function getAtE(set: MultiSetElements, i: number) {
function getAtE(set: MultiSetElements, i: number): IntTuple {
const { offsets, keys } = set;
const o = getOffsetIndex(offsets, i);
if (o >= offsets.length - 1) return 0;
if (o >= offsets.length - 1) return 0 as any;
const k = OrderedSet.getAt(keys, o);
const e = OrderedSet.getAt(set[k], i - offsets[o]);
return IntTuple.pack(k, e);
......@@ -480,7 +480,7 @@ function findUnion(sets: ArrayLike<MultiSetImpl>) {
if (typeof s !== 'number') unionInto(ret, s as MultiSetElements);
}
if (sizeI(ns as MultiSetImpl) > 0) {
if (typeof ns === 'number') unionIntoN(ret, ns);
if (typeof ns === 'number') unionIntoN(ret, ns as any);
else unionInto(ret, ns as MultiSetElements);
}
return ofObject(ret);
......@@ -494,14 +494,14 @@ function unionN(sets: ArrayLike<MultiSetImpl>, eCount: { count: number }) {
}
eCount.count = countE;
if (!countN) return MultiSet.Empty;
if (countN === sets.length) return ofTuples(sets as ArrayLike<number>);
if (countN === sets.length) return ofTuples(sets as ArrayLike<IntTuple>);
const packed = new Float64Array(countN);
let offset = 0;
for (let i = 0, _i = sets.length; i < _i; i++) {
const s = sets[i];
if (typeof s === 'number') packed[offset++] = s;
}
return ofTuples(packed);
return ofTuples(packed as any);
}
function unionInto(data: { [key: number]: OrderedSet }, a: MultiSetElements) {
......
......@@ -269,7 +269,7 @@ function unionRR(a: Range, b: Range) {
if (!sizeA) return b;
if (!sizeB) return a;
const minA = minR(a), minB = minR(b);
if (areRangesIntersecting(a as number, b as number)) return OrderedSet.ofRange(Math.min(minA, minB), Math.max(maxR(a), maxR(b)));
if (areRangesIntersecting(a, b)) return OrderedSet.ofRange(Math.min(minA, minB), Math.max(maxR(a), maxR(b)));
let lSize, lMin, rSize, rMin;
if (minR(a) < minR(b)) { lSize = sizeA; lMin = minA; rSize = sizeB; rMin = minB; }
else { lSize = sizeB; lMin = minB; rSize = sizeA; rMin = minA; }
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment