@isopodlabs/utilities 1.6.0 → 1.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bits.d.ts +109 -48
- package/dist/bits.js +550 -112
- package/package.json +1 -1
package/dist/bits.d.ts
CHANGED
|
@@ -3,36 +3,40 @@ export declare function highestSet32(x: number): number;
|
|
|
3
3
|
export declare function highestSet1024(x: number): number;
|
|
4
4
|
export declare function countSet32(x: number): number;
|
|
5
5
|
export declare function nthSet32(x: number, i: number): number;
|
|
6
|
+
export declare function reverse32(x: number): number;
|
|
6
7
|
export declare function highestSet(x: bigint | number): number;
|
|
7
8
|
export declare function lowestSet(x: number | bigint): number;
|
|
8
9
|
export declare function countSet(x: bigint | number): number;
|
|
9
10
|
export declare function nthSet(x: bigint | number, i: number): number;
|
|
11
|
+
export declare function reverse(x: number): number;
|
|
12
|
+
export declare function reverse(x: bigint): bigint;
|
|
10
13
|
export declare function highestClear(x: number | bigint): number;
|
|
11
14
|
export declare function lowestClear(x: number | bigint): number;
|
|
12
15
|
export declare function countClear(x: bigint | number): number;
|
|
13
16
|
export declare function clearLowest(x: bigint): bigint;
|
|
14
17
|
export declare function clearLowest(x: number): number;
|
|
15
18
|
export declare function clearLowest(x: bigint | number): bigint | number;
|
|
16
|
-
export interface
|
|
19
|
+
export interface BitSet {
|
|
17
20
|
test(a: number): boolean;
|
|
21
|
+
equals(other: this): boolean;
|
|
22
|
+
contains(other: this): boolean;
|
|
23
|
+
intersects(other: this): boolean;
|
|
18
24
|
countSet(): number;
|
|
19
25
|
nthSet(a: number): number;
|
|
20
|
-
complement():
|
|
21
|
-
intersect(other: this):
|
|
22
|
-
union(other: this):
|
|
23
|
-
xor(other: this):
|
|
24
|
-
|
|
26
|
+
complement(): BitSet;
|
|
27
|
+
intersect(other: this): BitSet;
|
|
28
|
+
union(other: this): BitSet;
|
|
29
|
+
xor(other: this): BitSet;
|
|
30
|
+
difference(other: this): BitSet;
|
|
25
31
|
next(a: number, set: boolean): number;
|
|
26
32
|
where(set: boolean, from?: number, to?: number): {
|
|
27
33
|
[Symbol.iterator](): Generator<number>;
|
|
28
34
|
};
|
|
29
|
-
ranges(): {
|
|
30
|
-
[Symbol.iterator](): Generator<number
|
|
35
|
+
ranges(set?: boolean): {
|
|
36
|
+
[Symbol.iterator](): Generator<[number, number]>;
|
|
31
37
|
};
|
|
32
|
-
slice(from: number, to?: number):
|
|
38
|
+
slice(from: number, to?: number): BitSet;
|
|
33
39
|
[Symbol.iterator](): Generator<number>;
|
|
34
|
-
}
|
|
35
|
-
export interface BitSet extends ImmutableBitSet {
|
|
36
40
|
set(a: number): void;
|
|
37
41
|
clear(a: number): void;
|
|
38
42
|
setRange(a: number, b: number): this;
|
|
@@ -41,32 +45,35 @@ export interface BitSet extends ImmutableBitSet {
|
|
|
41
45
|
selfIntersect(other: this): this;
|
|
42
46
|
selfUnion(other: this): this;
|
|
43
47
|
selfXor(other: this): this;
|
|
48
|
+
selfDifference(other: this): this;
|
|
44
49
|
}
|
|
45
|
-
export declare class
|
|
50
|
+
export declare class DenseBits implements BitSet {
|
|
46
51
|
protected bits: bigint;
|
|
47
52
|
constructor(bits?: bigint);
|
|
48
53
|
protected create(bits?: bigint): this;
|
|
54
|
+
static fromIndices<C extends new (bits: bigint, ...args: any[]) => any>(this: C, ...indices: number[]): InstanceType<C>;
|
|
49
55
|
get length(): number;
|
|
50
56
|
test(a: number): boolean;
|
|
57
|
+
equals(other: this): boolean;
|
|
58
|
+
contains(other: this): boolean;
|
|
59
|
+
intersects(other: this): boolean;
|
|
51
60
|
countSet(): number;
|
|
52
61
|
nthSet(a: number): number;
|
|
53
62
|
complement(): this;
|
|
54
|
-
intersect(other:
|
|
55
|
-
union(other:
|
|
56
|
-
xor(other:
|
|
57
|
-
|
|
63
|
+
intersect(other: DenseBits): this;
|
|
64
|
+
union(other: DenseBits): this;
|
|
65
|
+
xor(other: DenseBits): this;
|
|
66
|
+
difference(other: DenseBits): this;
|
|
58
67
|
next(a: number, set?: boolean): number;
|
|
59
68
|
where(set: boolean, from?: number, to?: number): {
|
|
60
69
|
[Symbol.iterator](): Generator<number>;
|
|
61
70
|
};
|
|
62
|
-
ranges(): {
|
|
63
|
-
[Symbol.iterator](): Generator<number
|
|
71
|
+
ranges(set?: boolean): {
|
|
72
|
+
[Symbol.iterator](): Generator<[number, number]>;
|
|
64
73
|
};
|
|
65
74
|
[Symbol.iterator](): Generator<number>;
|
|
66
|
-
toSparse():
|
|
67
|
-
slice(from: number, to?: number):
|
|
68
|
-
}
|
|
69
|
-
export declare class DenseBits extends ImmutableDenseBits implements BitSet {
|
|
75
|
+
toSparse(): SparseBits;
|
|
76
|
+
slice(from: number, to?: number): BitSet;
|
|
70
77
|
protected setMask(m: bigint): void;
|
|
71
78
|
protected clearMask(m: bigint): void;
|
|
72
79
|
set(a: number): void;
|
|
@@ -77,35 +84,83 @@ export declare class DenseBits extends ImmutableDenseBits implements BitSet {
|
|
|
77
84
|
selfIntersect(other: DenseBits): this;
|
|
78
85
|
selfUnion(other: DenseBits): this;
|
|
79
86
|
selfXor(other: DenseBits): this;
|
|
87
|
+
selfDifference(other: DenseBits): this;
|
|
80
88
|
}
|
|
81
|
-
export declare class
|
|
89
|
+
export declare class DenseBits32 implements BitSet {
|
|
90
|
+
protected bits: Uint32Array;
|
|
91
|
+
constructor(bits?: Uint32Array);
|
|
92
|
+
protected create(bits?: Uint32Array): this;
|
|
93
|
+
static fromIndices<C extends new (bits: Uint32Array, ...args: any[]) => any>(this: C, ...indices: number[]): InstanceType<C>;
|
|
94
|
+
get length(): number;
|
|
95
|
+
test(a: number): boolean;
|
|
96
|
+
equals(other: this): boolean;
|
|
97
|
+
contains(other: this): boolean;
|
|
98
|
+
intersects(other: this): boolean;
|
|
99
|
+
countSet(): number;
|
|
100
|
+
nthSet(a: number): number;
|
|
101
|
+
complement(): this;
|
|
102
|
+
intersect(other: DenseBits32): this;
|
|
103
|
+
union(other: DenseBits32): this;
|
|
104
|
+
xor(other: DenseBits32): this;
|
|
105
|
+
difference(other: DenseBits32): this;
|
|
106
|
+
next(a: number, set?: boolean): number;
|
|
107
|
+
where(set: boolean, from?: number, to?: number): {
|
|
108
|
+
[Symbol.iterator](): Generator<number>;
|
|
109
|
+
};
|
|
110
|
+
ranges(set?: boolean): {
|
|
111
|
+
[Symbol.iterator](): Generator<[number, number]>;
|
|
112
|
+
};
|
|
113
|
+
[Symbol.iterator](): Generator<number>;
|
|
114
|
+
toSparse(): SparseBits;
|
|
115
|
+
slice(from: number, to?: number): BitSet;
|
|
116
|
+
protected setMask(i: number, m: number): void;
|
|
117
|
+
protected clearMask(i: number, m: number): void;
|
|
118
|
+
set(a: number): void;
|
|
119
|
+
clear(a: number): void;
|
|
120
|
+
setRange(a: number, b: number): this;
|
|
121
|
+
clearRange(a: number, b: number): this;
|
|
122
|
+
selfComplement(): this;
|
|
123
|
+
selfIntersect(other: DenseBits32): this;
|
|
124
|
+
selfUnion(other: DenseBits32): this;
|
|
125
|
+
selfXor(other: DenseBits32): this;
|
|
126
|
+
selfDifference(other: DenseBits32): this;
|
|
127
|
+
clean(): this;
|
|
128
|
+
}
|
|
129
|
+
type SparseNumberArray = number[] | Record<number, number>;
|
|
130
|
+
type ExtraParams<T> = T extends new (bits: SparseNumberArray, ...args: infer P) => any ? P : never;
|
|
131
|
+
export declare class SparseBits implements BitSet {
|
|
82
132
|
protected bits: number[];
|
|
83
|
-
constructor(bits?:
|
|
84
|
-
protected create(bits?:
|
|
85
|
-
static fromEntries<
|
|
133
|
+
constructor(bits?: SparseNumberArray);
|
|
134
|
+
protected create(bits?: SparseNumberArray): this;
|
|
135
|
+
static fromEntries<C extends new (bits: SparseNumberArray, ...args: any[]) => any>(this: C, entries: Record<number, number> | [number, number][], ...extra: ExtraParams<C>): InstanceType<C>;
|
|
136
|
+
static fromIndices<C extends new (bits: SparseNumberArray, ...args: any[]) => any>(this: C, ...indices: number[]): InstanceType<C>;
|
|
137
|
+
static fromIndices<C extends new (bits: SparseNumberArray, ...args: any[]) => any>(this: C, indices: number[], ...extra: ExtraParams<C>): InstanceType<C>;
|
|
138
|
+
copy(): this;
|
|
139
|
+
empty(): boolean;
|
|
86
140
|
keys(): number[];
|
|
87
141
|
entries(): [number, number][];
|
|
88
142
|
test(a: number): boolean;
|
|
143
|
+
equals(other: this): boolean;
|
|
144
|
+
contains(other: SparseBits): boolean;
|
|
145
|
+
intersects(other: SparseBits): boolean;
|
|
89
146
|
countSet(): number;
|
|
90
147
|
nthSet(a: number): number;
|
|
91
|
-
complement():
|
|
92
|
-
intersect(other:
|
|
93
|
-
union(other:
|
|
94
|
-
xor(other:
|
|
95
|
-
|
|
148
|
+
complement(): SparseBits2;
|
|
149
|
+
intersect(other: SparseBits): this;
|
|
150
|
+
union(other: SparseBits): this;
|
|
151
|
+
xor(other: SparseBits): this;
|
|
152
|
+
difference(other: this): BitSet;
|
|
96
153
|
next(from: number, set?: boolean): number;
|
|
97
154
|
where(set: boolean, from?: number, to?: number): {
|
|
98
155
|
[Symbol.iterator]: () => Generator<number, void, unknown>;
|
|
99
156
|
};
|
|
100
|
-
ranges(): {
|
|
101
|
-
[Symbol.iterator]: () => Generator<number
|
|
157
|
+
ranges(set?: boolean): {
|
|
158
|
+
[Symbol.iterator]: () => Generator<[number, number], any, any>;
|
|
102
159
|
};
|
|
103
160
|
[Symbol.iterator](): Generator<number>;
|
|
104
161
|
clean(): this;
|
|
105
162
|
toDense(): DenseBits;
|
|
106
|
-
slice(from: number, to?: number):
|
|
107
|
-
}
|
|
108
|
-
export declare class SparseBits extends ImmutableSparseBits implements BitSet {
|
|
163
|
+
slice(from: number, to?: number): BitSet;
|
|
109
164
|
set(a: number): void;
|
|
110
165
|
clear(a: number): void;
|
|
111
166
|
setRange(a: number, b: number): this;
|
|
@@ -113,31 +168,35 @@ export declare class SparseBits extends ImmutableSparseBits implements BitSet {
|
|
|
113
168
|
selfIntersect(other: SparseBits): this;
|
|
114
169
|
selfUnion(other: SparseBits): this;
|
|
115
170
|
selfXor(other: SparseBits): this;
|
|
171
|
+
selfDifference(other: this): this;
|
|
116
172
|
}
|
|
117
|
-
export declare class
|
|
173
|
+
export declare class SparseBits2 extends SparseBits {
|
|
118
174
|
protected undef: number;
|
|
119
|
-
constructor(bits?:
|
|
120
|
-
protected create(bits?:
|
|
175
|
+
constructor(bits?: SparseNumberArray, initial?: boolean);
|
|
176
|
+
protected create(bits?: SparseNumberArray, initial?: boolean): this;
|
|
177
|
+
copy(): this;
|
|
178
|
+
empty(): boolean;
|
|
121
179
|
test(a: number): boolean;
|
|
180
|
+
equals(other: this): boolean;
|
|
181
|
+
contains(other: SparseBits2): boolean;
|
|
182
|
+
intersects(other: SparseBits2): boolean;
|
|
122
183
|
nthSet(a: number): number;
|
|
123
184
|
complement(): this;
|
|
124
|
-
intersect(other:
|
|
125
|
-
union(other:
|
|
126
|
-
xor(other:
|
|
127
|
-
|
|
185
|
+
intersect(other: SparseBits2): this;
|
|
186
|
+
union(other: SparseBits2): this;
|
|
187
|
+
xor(other: SparseBits2): this;
|
|
188
|
+
difference(other: SparseBits2): BitSet;
|
|
128
189
|
next(from: number, set?: boolean): number;
|
|
129
190
|
where(set: boolean, from?: number, to?: number): {
|
|
130
191
|
[Symbol.iterator]: () => Generator<number, void, unknown>;
|
|
131
192
|
};
|
|
132
|
-
ranges(): {
|
|
133
|
-
[Symbol.iterator]: () => Generator<number
|
|
193
|
+
ranges(set?: boolean): {
|
|
194
|
+
[Symbol.iterator]: () => Generator<[number, number], any, any>;
|
|
134
195
|
};
|
|
135
196
|
[Symbol.iterator](): Generator<number>;
|
|
136
197
|
clean(): this;
|
|
137
198
|
toDense(): DenseBits;
|
|
138
|
-
slice(from: number, to?: number):
|
|
139
|
-
}
|
|
140
|
-
export declare class SparseBits2 extends ImmutableSparseBits2 implements BitSet {
|
|
199
|
+
slice(from: number, to?: number): BitSet;
|
|
141
200
|
set(a: number): void;
|
|
142
201
|
clear(a: number): void;
|
|
143
202
|
setRange(a: number, b: number): this;
|
|
@@ -146,4 +205,6 @@ export declare class SparseBits2 extends ImmutableSparseBits2 implements BitSet
|
|
|
146
205
|
selfIntersect(other: SparseBits2): this;
|
|
147
206
|
selfUnion(other: SparseBits2): this;
|
|
148
207
|
selfXor(other: SparseBits2): this;
|
|
208
|
+
selfDifference(other: this): this;
|
|
149
209
|
}
|
|
210
|
+
export {};
|
package/dist/bits.js
CHANGED
|
@@ -3,16 +3,18 @@
|
|
|
3
3
|
// Bit twiddling functions
|
|
4
4
|
//-----------------------------------------------------------------------------
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
-
exports.SparseBits2 = exports.
|
|
6
|
+
exports.SparseBits2 = exports.SparseBits = exports.DenseBits32 = exports.DenseBits = void 0;
|
|
7
7
|
exports.lowestSet32 = lowestSet32;
|
|
8
8
|
exports.highestSet32 = highestSet32;
|
|
9
9
|
exports.highestSet1024 = highestSet1024;
|
|
10
10
|
exports.countSet32 = countSet32;
|
|
11
11
|
exports.nthSet32 = nthSet32;
|
|
12
|
+
exports.reverse32 = reverse32;
|
|
12
13
|
exports.highestSet = highestSet;
|
|
13
14
|
exports.lowestSet = lowestSet;
|
|
14
15
|
exports.countSet = countSet;
|
|
15
16
|
exports.nthSet = nthSet;
|
|
17
|
+
exports.reverse = reverse;
|
|
16
18
|
exports.highestClear = highestClear;
|
|
17
19
|
exports.lowestClear = lowestClear;
|
|
18
20
|
exports.countClear = countClear;
|
|
@@ -65,6 +67,13 @@ function nthSet32(x, i) {
|
|
|
65
67
|
++n;
|
|
66
68
|
return n;
|
|
67
69
|
}
|
|
70
|
+
function reverse32(x) {
|
|
71
|
+
x = ((x >> 1) & 0x55555555) | ((x & 0x55555555) << 1);
|
|
72
|
+
x = ((x >> 2) & 0x33333333) | ((x & 0x33333333) << 2);
|
|
73
|
+
x = ((x >> 4) & 0x0F0F0F0F) | ((x & 0x0F0F0F0F) << 4);
|
|
74
|
+
x = ((x >> 8) & 0x00FF00FF) | ((x & 0x00FF00FF) << 8);
|
|
75
|
+
return (x >> 16) | (x << 16);
|
|
76
|
+
}
|
|
68
77
|
/*
|
|
69
78
|
const testersShift: bigint[] = []; //32 << i
|
|
70
79
|
const testers: bigint[] = []; //1 << (32 << i)
|
|
@@ -239,6 +248,38 @@ function nthSet(x, i) {
|
|
|
239
248
|
}
|
|
240
249
|
return n;
|
|
241
250
|
}
|
|
251
|
+
function reverse(x) {
|
|
252
|
+
if (typeof x === 'number')
|
|
253
|
+
return reverse32(Number(x));
|
|
254
|
+
let k = 5;
|
|
255
|
+
for (let t = x >> 32n; t;)
|
|
256
|
+
t >>= BigInt(1 << k++);
|
|
257
|
+
let n = 1 << k;
|
|
258
|
+
let s = 0;
|
|
259
|
+
if (k === 5) {
|
|
260
|
+
s += highestSet32(Number(x));
|
|
261
|
+
}
|
|
262
|
+
else {
|
|
263
|
+
let t = x;
|
|
264
|
+
while (k >= 10) {
|
|
265
|
+
--k;
|
|
266
|
+
const b = t >> BigInt(1 << k);
|
|
267
|
+
if (b) {
|
|
268
|
+
s += 1 << k;
|
|
269
|
+
t = b;
|
|
270
|
+
}
|
|
271
|
+
}
|
|
272
|
+
s += highestSet1024(Number(t));
|
|
273
|
+
}
|
|
274
|
+
const shift = n - s;
|
|
275
|
+
let mask = (1n << BigInt(n)) - 1n;
|
|
276
|
+
while (n >>= 1) {
|
|
277
|
+
const nb = BigInt(n);
|
|
278
|
+
mask ^= (mask << nb);
|
|
279
|
+
x = ((x >> nb) & mask) | ((x << nb) & ~mask);
|
|
280
|
+
}
|
|
281
|
+
return x >> BigInt(shift);
|
|
282
|
+
}
|
|
242
283
|
// Returns the index of the highest clear bit
|
|
243
284
|
function highestClear(x) {
|
|
244
285
|
return highestSet(~x);
|
|
@@ -257,7 +298,7 @@ function clearLowest(x) {
|
|
|
257
298
|
//-----------------------------------------------------------------------------
|
|
258
299
|
// DenseBits - a dense bitset implementation using bigint
|
|
259
300
|
//-----------------------------------------------------------------------------
|
|
260
|
-
class
|
|
301
|
+
class DenseBits {
|
|
261
302
|
bits;
|
|
262
303
|
constructor(bits = 0n) {
|
|
263
304
|
this.bits = bits;
|
|
@@ -265,12 +306,27 @@ class ImmutableDenseBits {
|
|
|
265
306
|
create(bits) {
|
|
266
307
|
return new this.constructor(bits);
|
|
267
308
|
}
|
|
309
|
+
static fromIndices(...indices) {
|
|
310
|
+
let bits = 0n;
|
|
311
|
+
for (const i of indices)
|
|
312
|
+
bits |= 1n << BigInt(i);
|
|
313
|
+
return new this(bits);
|
|
314
|
+
}
|
|
268
315
|
get length() {
|
|
269
316
|
return highestSet(this.bits);
|
|
270
317
|
}
|
|
271
318
|
test(a) {
|
|
272
319
|
return !!(this.bits & (1n << BigInt(a)));
|
|
273
320
|
}
|
|
321
|
+
equals(other) {
|
|
322
|
+
return this.bits === other.bits;
|
|
323
|
+
}
|
|
324
|
+
contains(other) {
|
|
325
|
+
return (this.bits & other.bits) === other.bits;
|
|
326
|
+
}
|
|
327
|
+
intersects(other) {
|
|
328
|
+
return (this.bits & other.bits) !== 0n;
|
|
329
|
+
}
|
|
274
330
|
countSet() {
|
|
275
331
|
return countSet(this.bits);
|
|
276
332
|
}
|
|
@@ -289,8 +345,8 @@ class ImmutableDenseBits {
|
|
|
289
345
|
xor(other) {
|
|
290
346
|
return this.create(this.bits ^ other.bits);
|
|
291
347
|
}
|
|
292
|
-
|
|
293
|
-
return (this.bits & other.bits)
|
|
348
|
+
difference(other) {
|
|
349
|
+
return this.create(this.bits & ~other.bits);
|
|
294
350
|
}
|
|
295
351
|
next(a, set = true) {
|
|
296
352
|
let s = this.bits >> BigInt(a + 1);
|
|
@@ -312,17 +368,20 @@ class ImmutableDenseBits {
|
|
|
312
368
|
}
|
|
313
369
|
};
|
|
314
370
|
}
|
|
315
|
-
ranges() {
|
|
371
|
+
ranges(set = true) {
|
|
316
372
|
let bits = this.bits;
|
|
317
373
|
return {
|
|
318
374
|
*[Symbol.iterator]() {
|
|
319
375
|
let offset = 0;
|
|
320
376
|
while (bits) {
|
|
321
377
|
const i = highestSet(bits & -bits);
|
|
378
|
+
if (!set && offset + i > 1)
|
|
379
|
+
yield [offset ? offset - 1 : 0, offset + i - 1];
|
|
322
380
|
bits >>= BigInt(i);
|
|
323
381
|
const j = highestSet(~bits & (bits + 1n));
|
|
324
382
|
bits >>= BigInt(j);
|
|
325
|
-
|
|
383
|
+
if (set)
|
|
384
|
+
yield [offset + i - 1, offset + i + j - 1];
|
|
326
385
|
offset += i + j;
|
|
327
386
|
}
|
|
328
387
|
}
|
|
@@ -332,23 +391,20 @@ class ImmutableDenseBits {
|
|
|
332
391
|
yield* this.where(true);
|
|
333
392
|
}
|
|
334
393
|
toSparse() {
|
|
335
|
-
const sparse =
|
|
394
|
+
const sparse = [];
|
|
336
395
|
for (let bits = this.bits, i = 0; bits; bits >>= 32n, i++) {
|
|
337
396
|
const v = Number(bits & 0xffffffffn);
|
|
338
397
|
if (v)
|
|
339
398
|
sparse[i] = v;
|
|
340
399
|
}
|
|
341
|
-
return
|
|
400
|
+
return new SparseBits(sparse);
|
|
342
401
|
}
|
|
343
402
|
slice(from, to) {
|
|
344
403
|
return to === undefined
|
|
345
404
|
? this.create(this.bits >> BigInt(from))
|
|
346
405
|
: this.create(this.bits >> BigInt(from) & ((1n << BigInt(to - from)) - 1n));
|
|
347
406
|
}
|
|
348
|
-
|
|
349
|
-
exports.ImmutableDenseBits = ImmutableDenseBits;
|
|
350
|
-
;
|
|
351
|
-
class DenseBits extends ImmutableDenseBits {
|
|
407
|
+
// mutating methods
|
|
352
408
|
setMask(m) {
|
|
353
409
|
this.bits |= m;
|
|
354
410
|
}
|
|
@@ -385,23 +441,275 @@ class DenseBits extends ImmutableDenseBits {
|
|
|
385
441
|
this.bits ^= other.bits;
|
|
386
442
|
return this;
|
|
387
443
|
}
|
|
444
|
+
selfDifference(other) {
|
|
445
|
+
this.bits &= ~other.bits;
|
|
446
|
+
return this;
|
|
447
|
+
}
|
|
388
448
|
}
|
|
389
449
|
exports.DenseBits = DenseBits;
|
|
390
450
|
;
|
|
391
451
|
//-----------------------------------------------------------------------------
|
|
392
|
-
//
|
|
452
|
+
// DenseBits32 - a dense bitset implementation using Uint32Array
|
|
393
453
|
//-----------------------------------------------------------------------------
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
dest[k] = v;
|
|
454
|
+
class DenseBits32 {
|
|
455
|
+
bits;
|
|
456
|
+
constructor(bits = new Uint32Array(1)) {
|
|
457
|
+
this.bits = bits;
|
|
399
458
|
}
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
459
|
+
create(bits) {
|
|
460
|
+
return new this.constructor(bits);
|
|
461
|
+
}
|
|
462
|
+
static fromIndices(...indices) {
|
|
463
|
+
const max = Math.max(...indices);
|
|
464
|
+
const bits = new Uint32Array(Math.ceil((max + 1) / 32));
|
|
465
|
+
for (const i of indices)
|
|
466
|
+
bits[i >>> 5] |= 1 << (i & 31);
|
|
467
|
+
return new this(bits);
|
|
468
|
+
}
|
|
469
|
+
get length() {
|
|
470
|
+
const n = this.bits.length;
|
|
471
|
+
return highestSet32(this.bits[n - 1]) + (n - 1) * 32;
|
|
472
|
+
}
|
|
473
|
+
test(a) {
|
|
474
|
+
return !!(this.bits[a >>> 5] & (1 << (a & 31)));
|
|
475
|
+
}
|
|
476
|
+
equals(other) {
|
|
477
|
+
if (this.bits.length !== other.bits.length)
|
|
478
|
+
return false;
|
|
479
|
+
for (let i = 0; i < this.bits.length; i++) {
|
|
480
|
+
if (this.bits[i] !== other.bits[i])
|
|
481
|
+
return false;
|
|
482
|
+
}
|
|
483
|
+
return true;
|
|
484
|
+
}
|
|
485
|
+
contains(other) {
|
|
486
|
+
return other.bits.every((b, i) => (b & this.bits[i]) === b);
|
|
487
|
+
}
|
|
488
|
+
intersects(other) {
|
|
489
|
+
return this.bits.some((b, i) => (b & other.bits[i]) !== 0);
|
|
490
|
+
}
|
|
491
|
+
countSet() {
|
|
492
|
+
return this.bits.reduce((a, b) => a + countSet32(b), 0);
|
|
493
|
+
}
|
|
494
|
+
nthSet(a) {
|
|
495
|
+
for (let i = 0; i < this.bits.length; i++) {
|
|
496
|
+
const c = countSet32(this.bits[i]);
|
|
497
|
+
if (a < c)
|
|
498
|
+
return i * 32 + nthSet32(this.bits[i], a);
|
|
499
|
+
a -= c;
|
|
500
|
+
}
|
|
501
|
+
return -1;
|
|
502
|
+
}
|
|
503
|
+
complement() {
|
|
504
|
+
return this.create(this.bits.map(b => ~b));
|
|
505
|
+
}
|
|
506
|
+
intersect(other) {
|
|
507
|
+
return this.create(this.bits.map((b, i) => b & other.bits[i]));
|
|
508
|
+
}
|
|
509
|
+
union(other) {
|
|
510
|
+
if (other.bits.length > this.bits.length)
|
|
511
|
+
return this.create(other.bits.map((b, i) => b | this.bits[i]));
|
|
512
|
+
return this.create(this.bits.map((b, i) => b | other.bits[i]));
|
|
513
|
+
}
|
|
514
|
+
xor(other) {
|
|
515
|
+
if (other.bits.length > this.bits.length)
|
|
516
|
+
return this.create(other.bits.map((b, i) => b ^ this.bits[i]));
|
|
517
|
+
return this.create(this.bits.map((b, i) => b ^ other.bits[i]));
|
|
518
|
+
}
|
|
519
|
+
difference(other) {
|
|
520
|
+
return this.create(this.bits.map((b, i) => b & ~other.bits[i]));
|
|
521
|
+
}
|
|
522
|
+
next(a, set = true) {
|
|
523
|
+
++a;
|
|
524
|
+
const xor = set ? 0 : -1;
|
|
525
|
+
for (let i = a >>> 5; i < this.bits.length; i++) {
|
|
526
|
+
let b = this.bits[i] ^ xor;
|
|
527
|
+
if (b) {
|
|
528
|
+
if (i === (a >>> 5)) {
|
|
529
|
+
b &= -(1 << (a & 31));
|
|
530
|
+
if (!b)
|
|
531
|
+
continue;
|
|
532
|
+
}
|
|
533
|
+
return i * 32 + lowestSet32(b);
|
|
534
|
+
}
|
|
535
|
+
}
|
|
536
|
+
return -1;
|
|
537
|
+
}
|
|
538
|
+
where(set, from = -1, to) {
|
|
539
|
+
const bits = this.bits;
|
|
540
|
+
++from;
|
|
541
|
+
to = to === undefined ? bits.length * 32 : Math.min(to, bits.length * 32);
|
|
542
|
+
return {
|
|
543
|
+
*[Symbol.iterator]() {
|
|
544
|
+
const xor = set ? 0 : -1;
|
|
545
|
+
const end = (to + 31) >>> 5;
|
|
546
|
+
for (let i = from >>> 5; i < end; i++) {
|
|
547
|
+
let b = bits[i] ^ xor;
|
|
548
|
+
if (i === (from >>> 5))
|
|
549
|
+
b &= -(1 << (from & 31));
|
|
550
|
+
if (i === end - 1)
|
|
551
|
+
b &= (1 << (to & 31)) - 1;
|
|
552
|
+
while (b) {
|
|
553
|
+
yield i * 32 + lowestSet32(b);
|
|
554
|
+
b = b & (b - 1);
|
|
555
|
+
}
|
|
556
|
+
}
|
|
557
|
+
}
|
|
558
|
+
};
|
|
559
|
+
}
|
|
560
|
+
ranges(set = true) {
|
|
561
|
+
const bits = this.bits;
|
|
562
|
+
return {
|
|
563
|
+
*[Symbol.iterator]() {
|
|
564
|
+
let start = -1, end = 0;
|
|
565
|
+
for (let i = 0; i < bits.length; i++) {
|
|
566
|
+
let b = bits[i];
|
|
567
|
+
const c0 = +i * 32;
|
|
568
|
+
while ((start < 0 ? b : ~b) !== 0) {
|
|
569
|
+
if (start === -1) {
|
|
570
|
+
start = c0 + lowestSet32(b);
|
|
571
|
+
if (!set && end != start)
|
|
572
|
+
yield [end, start];
|
|
573
|
+
end = -1;
|
|
574
|
+
b = b | (b - 1);
|
|
575
|
+
}
|
|
576
|
+
else {
|
|
577
|
+
end = c0 + lowestSet32(~b);
|
|
578
|
+
if (set)
|
|
579
|
+
yield [start, end];
|
|
580
|
+
start = -1;
|
|
581
|
+
b = b & (b + 1);
|
|
582
|
+
}
|
|
583
|
+
}
|
|
584
|
+
}
|
|
585
|
+
if (set) {
|
|
586
|
+
if (start >= 0)
|
|
587
|
+
yield [start, bits.length * 32];
|
|
588
|
+
}
|
|
589
|
+
else {
|
|
590
|
+
yield [end, Infinity];
|
|
591
|
+
}
|
|
592
|
+
}
|
|
593
|
+
};
|
|
594
|
+
}
|
|
595
|
+
*[Symbol.iterator]() {
|
|
596
|
+
yield* this.where(true);
|
|
597
|
+
}
|
|
598
|
+
toSparse() {
|
|
599
|
+
const sparse = [];
|
|
600
|
+
for (let i = 0; i < this.bits.length; i++) {
|
|
601
|
+
const v = this.bits[i];
|
|
602
|
+
if (v)
|
|
603
|
+
sparse[i] = v;
|
|
604
|
+
}
|
|
605
|
+
return new SparseBits(sparse);
|
|
606
|
+
}
|
|
607
|
+
slice(from, to) {
|
|
608
|
+
to = to === undefined ? this.bits.length * 32 : Math.min(to, this.bits.length * 32);
|
|
609
|
+
const fromi = from >>> 5, toi = (to + 31) >>> 5;
|
|
610
|
+
const shift = from & 31;
|
|
611
|
+
const bits = shift === 0
|
|
612
|
+
? this.bits.slice(fromi, toi)
|
|
613
|
+
: this.bits.subarray(fromi, toi).map((b, i) => (b >>> shift) | (this.bits[fromi + i + 1] << (32 - shift)));
|
|
614
|
+
const maskBits = (to - from) & 31;
|
|
615
|
+
if (maskBits)
|
|
616
|
+
bits[bits.length - 1] &= (1 << maskBits) - 1;
|
|
617
|
+
return this.create(bits);
|
|
618
|
+
}
|
|
619
|
+
// mutating methods
|
|
620
|
+
setMask(i, m) {
|
|
621
|
+
if (i >= this.bits.length) {
|
|
622
|
+
const bits = new Uint32Array(i + 1);
|
|
623
|
+
bits.set(this.bits);
|
|
624
|
+
this.bits = bits;
|
|
625
|
+
}
|
|
626
|
+
this.bits[i] |= m;
|
|
627
|
+
}
|
|
628
|
+
clearMask(i, m) {
|
|
629
|
+
if (i < this.bits.length)
|
|
630
|
+
this.bits[i] &= ~m;
|
|
631
|
+
}
|
|
632
|
+
set(a) {
|
|
633
|
+
this.setMask(a >>> 5, 1 << (a & 31));
|
|
634
|
+
}
|
|
635
|
+
clear(a) {
|
|
636
|
+
this.clearMask(a >>> 5, 1 << (a & 31));
|
|
637
|
+
}
|
|
638
|
+
setRange(a, b) {
|
|
639
|
+
const ai = a >>> 5, bi = b >>> 5;
|
|
640
|
+
if (ai === bi) {
|
|
641
|
+
this.setMask(ai, (1 << (b & 31)) - (1 << (a & 31)));
|
|
642
|
+
}
|
|
643
|
+
else {
|
|
644
|
+
this.setMask(bi, (1 << (b & 31)) - 1);
|
|
645
|
+
this.setMask(ai, -(1 << (a & 31)));
|
|
646
|
+
for (let i = ai + 1; i < bi; i++)
|
|
647
|
+
this.bits[i] = -1;
|
|
648
|
+
}
|
|
649
|
+
return this;
|
|
650
|
+
}
|
|
651
|
+
clearRange(a, b) {
|
|
652
|
+
const ai = a >>> 5, bi = b >>> 5;
|
|
653
|
+
if (ai < this.bits.length) {
|
|
654
|
+
if (ai === bi) {
|
|
655
|
+
this.clearMask(ai, (1 << (b & 31)) - (1 << (a & 31)));
|
|
656
|
+
}
|
|
657
|
+
else {
|
|
658
|
+
this.clearMask(ai, -(1 << (a & 31)));
|
|
659
|
+
if (bi >= this.bits.length) {
|
|
660
|
+
this.bits = this.bits.slice(0, ai + 1);
|
|
661
|
+
}
|
|
662
|
+
else {
|
|
663
|
+
for (let i = ai + 1; i < bi; i++)
|
|
664
|
+
this.bits[i] = 0;
|
|
665
|
+
this.clearMask(bi, (1 << (b & 31)) - 1);
|
|
666
|
+
}
|
|
667
|
+
}
|
|
668
|
+
}
|
|
669
|
+
return this;
|
|
403
670
|
}
|
|
404
|
-
|
|
671
|
+
selfComplement() {
|
|
672
|
+
this.bits = this.bits.map(b => ~b);
|
|
673
|
+
return this;
|
|
674
|
+
}
|
|
675
|
+
selfIntersect(other) {
|
|
676
|
+
this.bits = this.bits.map((b, i) => b & other.bits[i]);
|
|
677
|
+
return this;
|
|
678
|
+
}
|
|
679
|
+
selfUnion(other) {
|
|
680
|
+
this.bits = other.bits.length > this.bits.length
|
|
681
|
+
? other.bits.map((b, i) => b | this.bits[i])
|
|
682
|
+
: this.bits.map((b, i) => b | other.bits[i]);
|
|
683
|
+
return this;
|
|
684
|
+
}
|
|
685
|
+
selfXor(other) {
|
|
686
|
+
this.bits = other.bits.length > this.bits.length
|
|
687
|
+
? other.bits.map((b, i) => b ^ this.bits[i])
|
|
688
|
+
: this.bits.map((b, i) => b ^ other.bits[i]);
|
|
689
|
+
return this;
|
|
690
|
+
}
|
|
691
|
+
selfDifference(other) {
|
|
692
|
+
this.bits = this.bits.map((b, i) => b & ~other.bits[i]);
|
|
693
|
+
return this;
|
|
694
|
+
}
|
|
695
|
+
clean() {
|
|
696
|
+
let i = this.bits.length;
|
|
697
|
+
while (i-- && this.bits[i] === 0)
|
|
698
|
+
;
|
|
699
|
+
this.bits = this.bits.slice(0, i + 1);
|
|
700
|
+
return this;
|
|
701
|
+
}
|
|
702
|
+
}
|
|
703
|
+
exports.DenseBits32 = DenseBits32;
|
|
704
|
+
;
|
|
705
|
+
//-----------------------------------------------------------------------------
|
|
706
|
+
// SparseBits - a sparse bitset where each entry in the 'bits' array represents 32 bits
|
|
707
|
+
//-----------------------------------------------------------------------------
|
|
708
|
+
function sparseFromIndices(indices) {
|
|
709
|
+
const bits = [];
|
|
710
|
+
for (const i of indices)
|
|
711
|
+
bits[i >> 5] |= 1 << (i & 0x1f);
|
|
712
|
+
return bits;
|
|
405
713
|
}
|
|
406
714
|
function sparseCopyUndefined(bits, other, xor = 0) {
|
|
407
715
|
for (const i in other) {
|
|
@@ -410,6 +718,13 @@ function sparseCopyUndefined(bits, other, xor = 0) {
|
|
|
410
718
|
}
|
|
411
719
|
return bits;
|
|
412
720
|
}
|
|
721
|
+
function sparseDeleteUndefined(bits, other) {
|
|
722
|
+
for (const i in bits) {
|
|
723
|
+
if (other[i] === undefined)
|
|
724
|
+
delete bits[i];
|
|
725
|
+
}
|
|
726
|
+
return bits;
|
|
727
|
+
}
|
|
413
728
|
function sparseClean(bits, undef = 0) {
|
|
414
729
|
for (const i in bits) {
|
|
415
730
|
if (bits[i] === undef)
|
|
@@ -503,14 +818,41 @@ function sparseNthSet(bits, a, undef = 0) {
|
|
|
503
818
|
function sparseComplement(bits) {
|
|
504
819
|
return bits.map(b => ~b);
|
|
505
820
|
}
|
|
506
|
-
function sparseIntersect(bits, other
|
|
507
|
-
|
|
821
|
+
function sparseIntersect(bits, other) {
|
|
822
|
+
const result = [];
|
|
823
|
+
for (const i in bits) {
|
|
824
|
+
if (other[i] !== undefined) {
|
|
825
|
+
result[i] = bits[i] & other[i];
|
|
826
|
+
}
|
|
827
|
+
}
|
|
828
|
+
return result;
|
|
508
829
|
}
|
|
509
|
-
function sparseUnion(bits, other
|
|
510
|
-
|
|
830
|
+
function sparseUnion(bits, other) {
|
|
831
|
+
const result = [];
|
|
832
|
+
for (const i in bits) {
|
|
833
|
+
if (other[i] !== undefined) {
|
|
834
|
+
result[i] = bits[i] | other[i];
|
|
835
|
+
}
|
|
836
|
+
}
|
|
837
|
+
return result;
|
|
511
838
|
}
|
|
512
|
-
function sparseXor(bits, other
|
|
513
|
-
|
|
839
|
+
function sparseXor(bits, other) {
|
|
840
|
+
const result = [];
|
|
841
|
+
for (const i in bits) {
|
|
842
|
+
if (other[i] !== undefined) {
|
|
843
|
+
result[i] = bits[i] ^ other[i];
|
|
844
|
+
}
|
|
845
|
+
}
|
|
846
|
+
return result;
|
|
847
|
+
}
|
|
848
|
+
function sparseDifference(bits, other) {
|
|
849
|
+
const result = [];
|
|
850
|
+
for (const i in bits) {
|
|
851
|
+
if (other[i] !== undefined) {
|
|
852
|
+
result[i] = bits[i] & ~other[i];
|
|
853
|
+
}
|
|
854
|
+
}
|
|
855
|
+
return result;
|
|
514
856
|
}
|
|
515
857
|
function sparseSelfComplement(bits) {
|
|
516
858
|
for (const i in bits)
|
|
@@ -519,19 +861,45 @@ function sparseSelfComplement(bits) {
|
|
|
519
861
|
}
|
|
520
862
|
function sparseSelfIntersect(bits, other) {
|
|
521
863
|
for (const i in bits)
|
|
522
|
-
|
|
864
|
+
if (other[i] !== undefined)
|
|
865
|
+
bits[i] &= other[i];
|
|
523
866
|
return bits;
|
|
524
867
|
}
|
|
525
868
|
function sparseSelfUnion(bits, other) {
|
|
526
869
|
for (const i in bits)
|
|
527
|
-
|
|
870
|
+
if (other[i] !== undefined)
|
|
871
|
+
bits[i] |= other[i];
|
|
528
872
|
return bits;
|
|
529
873
|
}
|
|
530
874
|
function sparseSelfXor(bits, other) {
|
|
531
875
|
for (const i in bits)
|
|
532
|
-
|
|
876
|
+
if (other[i] !== undefined)
|
|
877
|
+
bits[i] ^= other[i];
|
|
533
878
|
return bits;
|
|
534
879
|
}
|
|
880
|
+
function sparseSelfDifference(bits, other) {
|
|
881
|
+
for (const i in bits)
|
|
882
|
+
if (other[i] !== undefined)
|
|
883
|
+
bits[i] &= ~other[i];
|
|
884
|
+
return bits;
|
|
885
|
+
}
|
|
886
|
+
function sparseEquals(bits, other) {
|
|
887
|
+
const ka = Object.keys(bits), kb = Object.keys(other);
|
|
888
|
+
if (ka.length !== kb.length)
|
|
889
|
+
return false;
|
|
890
|
+
for (const k of ka) {
|
|
891
|
+
if (bits[+k] !== other[+k])
|
|
892
|
+
return false;
|
|
893
|
+
}
|
|
894
|
+
return true;
|
|
895
|
+
}
|
|
896
|
+
function sparseIntersects(bits, other, undef = 0) {
|
|
897
|
+
for (const i in bits) {
|
|
898
|
+
if ((bits[i] & (other[i] ?? undef)))
|
|
899
|
+
return true;
|
|
900
|
+
}
|
|
901
|
+
return false;
|
|
902
|
+
}
|
|
535
903
|
function sparseContains(bits, other, undef = 0) {
|
|
536
904
|
for (const i in other) {
|
|
537
905
|
if (other[i] & ~(bits[i] ?? undef))
|
|
@@ -541,11 +909,12 @@ function sparseContains(bits, other, undef = 0) {
|
|
|
541
909
|
}
|
|
542
910
|
function sparseNext(bits, from, set = true, undef = 0) {
|
|
543
911
|
++from;
|
|
912
|
+
const from32 = from >> 5;
|
|
913
|
+
const fromM = 1 << (from & 0x1f);
|
|
544
914
|
if (undef ? !set : set) {
|
|
545
|
-
const ai = from >> 5;
|
|
546
915
|
for (const i in bits) {
|
|
547
|
-
if (+i >=
|
|
548
|
-
const v = bits[i] ^ undef;
|
|
916
|
+
if (+i >= from32) {
|
|
917
|
+
const v = (bits[i] ^ undef) & (+i === from32 ? -fromM : -1);
|
|
549
918
|
if (v)
|
|
550
919
|
return (+i << 5) + lowestSet32(v);
|
|
551
920
|
}
|
|
@@ -553,13 +922,12 @@ function sparseNext(bits, from, set = true, undef = 0) {
|
|
|
553
922
|
return -1;
|
|
554
923
|
}
|
|
555
924
|
else {
|
|
556
|
-
|
|
557
|
-
if (bits[i] === undefined)
|
|
925
|
+
if (bits[from32] === undefined)
|
|
558
926
|
return from;
|
|
559
|
-
let
|
|
927
|
+
let i = from32;
|
|
928
|
+
let v = (bits[i] ^ undef) | (fromM - 1);
|
|
560
929
|
while (!v) {
|
|
561
|
-
++i
|
|
562
|
-
if (bits[i] === undefined)
|
|
930
|
+
if (bits[++i] === undefined)
|
|
563
931
|
break;
|
|
564
932
|
v = bits[i] ^ undef;
|
|
565
933
|
}
|
|
@@ -572,94 +940,93 @@ function* sparseWhere(bits, set, from = -1, to, undef = 0) {
|
|
|
572
940
|
const to32 = to === undefined ? Infinity : to >> 5;
|
|
573
941
|
const fromM = 1 << (from & 0x1f);
|
|
574
942
|
const toM = to === undefined ? 0 : 1 << (to & 0x1f);
|
|
943
|
+
function* block(i, v) {
|
|
944
|
+
while (v) {
|
|
945
|
+
yield (i << 5) + lowestSet32(v);
|
|
946
|
+
v &= v - 1;
|
|
947
|
+
}
|
|
948
|
+
}
|
|
575
949
|
if (undef ? !set : set) {
|
|
576
950
|
for (const k in bits) {
|
|
577
951
|
const i = +k;
|
|
578
|
-
if (i >= to32)
|
|
579
|
-
break;
|
|
580
952
|
if (i >= from32) {
|
|
953
|
+
if (i >= to32)
|
|
954
|
+
break;
|
|
581
955
|
let v = bits[i] ^ undef;
|
|
582
956
|
if (i === from32)
|
|
583
957
|
v &= -fromM;
|
|
584
958
|
if (i === to32)
|
|
585
959
|
v &= (toM - 1);
|
|
586
|
-
|
|
587
|
-
yield (i << 5) + lowestSet32(v);
|
|
588
|
-
v = v & (v - 1);
|
|
589
|
-
}
|
|
960
|
+
yield* block(i, v);
|
|
590
961
|
}
|
|
591
962
|
}
|
|
592
963
|
}
|
|
593
964
|
else {
|
|
594
965
|
if (to32 > from32) {
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
yield (i << 5) + lowestSet32(v);
|
|
600
|
-
}
|
|
601
|
-
for (let v = ((bits[to32] ?? undef) ^ ~undef) & (toM - 1); v; v = v & (v - 1))
|
|
602
|
-
yield (to32 << 5) + lowestSet32(v);
|
|
966
|
+
yield* block(from32, ((bits[from32] ?? undef) ^ ~undef) & -fromM);
|
|
967
|
+
for (let i = from32 + 1; i < to32; i++)
|
|
968
|
+
yield* block(i, (bits[i] ?? undef) ^ ~undef);
|
|
969
|
+
yield* block(to32, ((bits[to32] ?? undef) ^ ~undef) & (toM - 1));
|
|
603
970
|
}
|
|
604
971
|
else if (to32 === from32) {
|
|
605
|
-
|
|
606
|
-
yield (from32 << 5) + lowestSet32(v);
|
|
972
|
+
yield* block(from32, ((bits[from32] ?? undef) ^ ~undef) & (-fromM & (toM - 1)));
|
|
607
973
|
}
|
|
608
974
|
}
|
|
609
975
|
}
|
|
610
|
-
function* sparseRanges(bits, undef = 0) {
|
|
976
|
+
function* sparseRanges(bits, set, undef = 0) {
|
|
611
977
|
let start = -1, end = 0;
|
|
978
|
+
let other = undef ? set : !set;
|
|
612
979
|
for (const i in bits) {
|
|
613
980
|
let b = bits[i] ^ undef;
|
|
614
981
|
const c0 = +i * 32;
|
|
615
982
|
while ((start < 0 ? b : ~b) !== 0) {
|
|
616
983
|
if (start === -1) {
|
|
617
984
|
start = c0 + lowestSet32(b);
|
|
618
|
-
if (
|
|
985
|
+
if (other && end != start)
|
|
619
986
|
yield [end, start];
|
|
620
987
|
end = -1;
|
|
621
988
|
b = b | (b - 1);
|
|
622
989
|
}
|
|
623
990
|
else {
|
|
624
991
|
end = c0 + lowestSet32(~b);
|
|
625
|
-
if (!
|
|
992
|
+
if (!other)
|
|
626
993
|
yield [start, end];
|
|
627
994
|
start = -1;
|
|
628
995
|
b = b & (b + 1);
|
|
629
996
|
}
|
|
630
997
|
}
|
|
631
998
|
if (start >= 0 && bits[+i + 1] === undefined) {
|
|
632
|
-
if (!
|
|
999
|
+
if (!other)
|
|
633
1000
|
yield [start, c0 + 32];
|
|
634
1001
|
start = -1;
|
|
635
1002
|
}
|
|
636
1003
|
}
|
|
637
|
-
if (
|
|
1004
|
+
if (other)
|
|
638
1005
|
yield [end, Infinity];
|
|
639
1006
|
}
|
|
640
1007
|
function sparseSlice(bits, from, to) {
|
|
641
1008
|
const from32 = from >> 5;
|
|
642
|
-
const
|
|
643
|
-
const
|
|
644
|
-
const
|
|
1009
|
+
const fromM = 1 << (from & 0x1f);
|
|
1010
|
+
const to32 = to !== undefined ? to >> 5 : Infinity;
|
|
1011
|
+
const toM = to !== undefined ? 1 << (to & 0x1f) : 0;
|
|
645
1012
|
const result = [];
|
|
646
|
-
for (const
|
|
647
|
-
const
|
|
648
|
-
if (
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
1013
|
+
for (const k in bits) {
|
|
1014
|
+
const i = +k;
|
|
1015
|
+
if (i >= from32) {
|
|
1016
|
+
if (i > to32)
|
|
1017
|
+
break;
|
|
1018
|
+
let b = bits[k];
|
|
1019
|
+
if (i === from32)
|
|
1020
|
+
b &= -fromM;
|
|
1021
|
+
if (i === to32)
|
|
1022
|
+
b &= toM - 1;
|
|
1023
|
+
if (b !== 0)
|
|
1024
|
+
result[k] = b;
|
|
1025
|
+
}
|
|
659
1026
|
}
|
|
660
1027
|
return result;
|
|
661
1028
|
}
|
|
662
|
-
class
|
|
1029
|
+
class SparseBits {
|
|
663
1030
|
bits;
|
|
664
1031
|
constructor(bits = []) {
|
|
665
1032
|
this.bits = bits;
|
|
@@ -667,10 +1034,23 @@ class ImmutableSparseBits {
|
|
|
667
1034
|
create(bits = []) {
|
|
668
1035
|
return new this.constructor(bits);
|
|
669
1036
|
}
|
|
670
|
-
static fromEntries(entries, ...
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
1037
|
+
static fromEntries(entries, ...extra) {
|
|
1038
|
+
return new this(Array.isArray(entries) ? Object.fromEntries(entries) : entries, ...extra);
|
|
1039
|
+
}
|
|
1040
|
+
static fromIndices(indicesOrFirst, ...rest) {
|
|
1041
|
+
return Array.isArray(indicesOrFirst)
|
|
1042
|
+
? new this(sparseFromIndices(indicesOrFirst), ...rest)
|
|
1043
|
+
: new this(sparseFromIndices([indicesOrFirst, ...rest]));
|
|
1044
|
+
}
|
|
1045
|
+
copy() {
|
|
1046
|
+
return this.create({ ...this.bits });
|
|
1047
|
+
}
|
|
1048
|
+
empty() {
|
|
1049
|
+
for (const i in this.bits) {
|
|
1050
|
+
if (this.bits[i] !== 0)
|
|
1051
|
+
return false;
|
|
1052
|
+
}
|
|
1053
|
+
return true;
|
|
674
1054
|
}
|
|
675
1055
|
keys() {
|
|
676
1056
|
return Object.keys(this.bits).map(k => +k);
|
|
@@ -681,6 +1061,15 @@ class ImmutableSparseBits {
|
|
|
681
1061
|
test(a) {
|
|
682
1062
|
return sparseTest(this.bits, a);
|
|
683
1063
|
}
|
|
1064
|
+
equals(other) {
|
|
1065
|
+
return sparseEquals(this.bits, other.bits);
|
|
1066
|
+
}
|
|
1067
|
+
contains(other) {
|
|
1068
|
+
return sparseContains(this.bits, other.bits);
|
|
1069
|
+
}
|
|
1070
|
+
intersects(other) {
|
|
1071
|
+
return sparseIntersects(this.bits, other.bits);
|
|
1072
|
+
}
|
|
684
1073
|
countSet() {
|
|
685
1074
|
return sparseCountSet(this.bits);
|
|
686
1075
|
}
|
|
@@ -688,19 +1077,19 @@ class ImmutableSparseBits {
|
|
|
688
1077
|
return sparseNthSet(this.bits, a);
|
|
689
1078
|
}
|
|
690
1079
|
complement() {
|
|
691
|
-
return new
|
|
1080
|
+
return new SparseBits2(sparseComplement(this.bits), true);
|
|
692
1081
|
}
|
|
693
1082
|
intersect(other) {
|
|
694
1083
|
return this.create(sparseIntersect(this.bits, other.bits));
|
|
695
1084
|
}
|
|
696
1085
|
union(other) {
|
|
697
|
-
return this.create(sparseCopyUndefined(sparseUnion(this.bits, other.bits), other.bits));
|
|
1086
|
+
return this.create(sparseCopyUndefined(sparseCopyUndefined(sparseUnion(this.bits, other.bits), other.bits), this.bits));
|
|
698
1087
|
}
|
|
699
1088
|
xor(other) {
|
|
700
|
-
return this.create(sparseCopyUndefined(sparseXor(this.bits, other.bits), other.bits));
|
|
1089
|
+
return this.create(sparseCopyUndefined(sparseCopyUndefined(sparseXor(this.bits, other.bits), other.bits, -1), this.bits, -1));
|
|
701
1090
|
}
|
|
702
|
-
|
|
703
|
-
return
|
|
1091
|
+
difference(other) {
|
|
1092
|
+
return this.create(sparseCopyUndefined(sparseDifference(this.bits, other.bits), this.bits));
|
|
704
1093
|
}
|
|
705
1094
|
next(from, set = true) {
|
|
706
1095
|
return sparseNext(this.bits, from, set);
|
|
@@ -710,9 +1099,9 @@ class ImmutableSparseBits {
|
|
|
710
1099
|
[Symbol.iterator]: () => sparseWhere(this.bits, set, from, to)
|
|
711
1100
|
};
|
|
712
1101
|
}
|
|
713
|
-
ranges() {
|
|
1102
|
+
ranges(set = true) {
|
|
714
1103
|
return {
|
|
715
|
-
[Symbol.iterator]: () => sparseRanges(this.bits)
|
|
1104
|
+
[Symbol.iterator]: () => sparseRanges(this.bits, set)
|
|
716
1105
|
};
|
|
717
1106
|
}
|
|
718
1107
|
*[Symbol.iterator]() {
|
|
@@ -729,11 +1118,9 @@ class ImmutableSparseBits {
|
|
|
729
1118
|
return new DenseBits(bits);
|
|
730
1119
|
}
|
|
731
1120
|
slice(from, to) {
|
|
732
|
-
return this.create(sparseSlice(this.bits, from, to));
|
|
1121
|
+
return this.create(sparseSlice(this.bits, from, to)); // ?? this.bits.length * 32));
|
|
733
1122
|
}
|
|
734
|
-
|
|
735
|
-
exports.ImmutableSparseBits = ImmutableSparseBits;
|
|
736
|
-
class SparseBits extends ImmutableSparseBits {
|
|
1123
|
+
//mutating methods
|
|
737
1124
|
set(a) {
|
|
738
1125
|
sparseSetMask(this.bits, a >> 5, 1 << (a & 0x1f));
|
|
739
1126
|
}
|
|
@@ -750,6 +1137,7 @@ class SparseBits extends ImmutableSparseBits {
|
|
|
750
1137
|
}
|
|
751
1138
|
selfIntersect(other) {
|
|
752
1139
|
sparseSelfIntersect(this.bits, other.bits);
|
|
1140
|
+
sparseDeleteUndefined(this.bits, other.bits);
|
|
753
1141
|
return this;
|
|
754
1142
|
}
|
|
755
1143
|
selfUnion(other) {
|
|
@@ -760,24 +1148,47 @@ class SparseBits extends ImmutableSparseBits {
|
|
|
760
1148
|
sparseCopyUndefined(sparseSelfXor(this.bits, other.bits), other.bits);
|
|
761
1149
|
return this;
|
|
762
1150
|
}
|
|
1151
|
+
selfDifference(other) {
|
|
1152
|
+
sparseSelfDifference(this.bits, other.bits);
|
|
1153
|
+
return this;
|
|
1154
|
+
}
|
|
763
1155
|
}
|
|
764
1156
|
exports.SparseBits = SparseBits;
|
|
765
1157
|
;
|
|
766
1158
|
//-----------------------------------------------------------------------------
|
|
767
|
-
// SparseBits2 as above, with
|
|
1159
|
+
// SparseBits2 as above, with 'undef' indicating whether undefined entries are treated as 0 or 0xffffffff
|
|
768
1160
|
//-----------------------------------------------------------------------------
|
|
769
|
-
class
|
|
1161
|
+
class SparseBits2 extends SparseBits {
|
|
770
1162
|
undef;
|
|
771
1163
|
constructor(bits = [], initial = false) {
|
|
772
1164
|
super(bits);
|
|
773
1165
|
this.undef = initial ? -1 : 0;
|
|
774
1166
|
}
|
|
775
|
-
create(bits = [],
|
|
776
|
-
return new this.constructor(bits,
|
|
1167
|
+
create(bits = [], initial = false) {
|
|
1168
|
+
return new this.constructor(bits, initial);
|
|
1169
|
+
}
|
|
1170
|
+
copy() {
|
|
1171
|
+
return this.create({ ...this.bits }, !!this.undef);
|
|
1172
|
+
}
|
|
1173
|
+
empty() {
|
|
1174
|
+
return !this.undef && super.empty();
|
|
777
1175
|
}
|
|
778
1176
|
test(a) {
|
|
779
1177
|
return sparseTest(this.bits, a, this.undef);
|
|
780
1178
|
}
|
|
1179
|
+
equals(other) {
|
|
1180
|
+
return this.undef === other.undef && sparseEquals(this.bits, other.bits);
|
|
1181
|
+
}
|
|
1182
|
+
contains(other) {
|
|
1183
|
+
if (other.undef && !this.undef)
|
|
1184
|
+
return false;
|
|
1185
|
+
return sparseContains(this.bits, other.bits, this.undef);
|
|
1186
|
+
}
|
|
1187
|
+
intersects(other) {
|
|
1188
|
+
if (this.undef)
|
|
1189
|
+
return !!other.undef || sparseIntersects(other.bits, this.bits, this.undef);
|
|
1190
|
+
return sparseIntersects(this.bits, other.bits, other.undef);
|
|
1191
|
+
}
|
|
781
1192
|
nthSet(a) {
|
|
782
1193
|
return sparseNthSet(this.bits, a, this.undef);
|
|
783
1194
|
}
|
|
@@ -785,22 +1196,33 @@ class ImmutableSparseBits2 extends ImmutableSparseBits {
|
|
|
785
1196
|
return this.create(sparseComplement(this.bits), this.undef === 0);
|
|
786
1197
|
}
|
|
787
1198
|
intersect(other) {
|
|
1199
|
+
const bits = sparseIntersect(this.bits, other.bits);
|
|
1200
|
+
if (other.undef)
|
|
1201
|
+
sparseCopyUndefined(bits, this.bits);
|
|
788
1202
|
if (this.undef)
|
|
789
|
-
return this.create(sparseCopyUndefined(
|
|
790
|
-
return this.create(
|
|
1203
|
+
return this.create(sparseCopyUndefined(bits, other.bits), !!other.undef);
|
|
1204
|
+
return this.create(bits, false);
|
|
791
1205
|
}
|
|
792
1206
|
union(other) {
|
|
1207
|
+
const bits = sparseUnion(this.bits, other.bits);
|
|
1208
|
+
if (!other.undef)
|
|
1209
|
+
sparseCopyUndefined(bits, this.bits);
|
|
793
1210
|
if (this.undef)
|
|
794
|
-
return this.create(
|
|
795
|
-
return this.create(sparseCopyUndefined(
|
|
1211
|
+
return this.create(bits, true);
|
|
1212
|
+
return this.create(sparseCopyUndefined(bits, other.bits), !!other.undef);
|
|
796
1213
|
}
|
|
797
1214
|
xor(other) {
|
|
798
|
-
return this.create(sparseCopyUndefined(sparseXor(this.bits, other.bits), other.bits, this.undef), !!(this.undef ^ other.undef));
|
|
1215
|
+
return this.create(sparseCopyUndefined(sparseCopyUndefined(sparseXor(this.bits, other.bits), other.bits, this.undef), this.bits, other.undef), !!(this.undef ^ other.undef));
|
|
799
1216
|
}
|
|
800
|
-
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
1217
|
+
difference(other) {
|
|
1218
|
+
const bits = sparseDifference(this.bits, other.bits);
|
|
1219
|
+
if (!other.undef) {
|
|
1220
|
+
sparseCopyUndefined(bits, this.bits);
|
|
1221
|
+
return this.create(bits, !!this.undef);
|
|
1222
|
+
}
|
|
1223
|
+
if (this.undef)
|
|
1224
|
+
sparseCopyUndefined(bits, other.bits, -1);
|
|
1225
|
+
return this.create(bits, false);
|
|
804
1226
|
}
|
|
805
1227
|
next(from, set = true) {
|
|
806
1228
|
return sparseNext(this.bits, from, set, this.undef);
|
|
@@ -810,9 +1232,9 @@ class ImmutableSparseBits2 extends ImmutableSparseBits {
|
|
|
810
1232
|
[Symbol.iterator]: () => sparseWhere(this.bits, set, from, to, this.undef)
|
|
811
1233
|
};
|
|
812
1234
|
}
|
|
813
|
-
ranges() {
|
|
1235
|
+
ranges(set = true) {
|
|
814
1236
|
return {
|
|
815
|
-
[Symbol.iterator]: () => sparseRanges(this.bits, this.undef)
|
|
1237
|
+
[Symbol.iterator]: () => sparseRanges(this.bits, set, this.undef)
|
|
816
1238
|
};
|
|
817
1239
|
}
|
|
818
1240
|
*[Symbol.iterator]() {
|
|
@@ -836,11 +1258,12 @@ class ImmutableSparseBits2 extends ImmutableSparseBits {
|
|
|
836
1258
|
return new DenseBits(bits);
|
|
837
1259
|
}
|
|
838
1260
|
slice(from, to) {
|
|
839
|
-
|
|
1261
|
+
//to ??= this.bits.length * 32;
|
|
1262
|
+
return this.undef
|
|
1263
|
+
? this.create(sparseSelfComplement(sparseSlice(sparseComplement(this.bits), from, to)), true)
|
|
1264
|
+
: this.create(sparseSlice(this.bits, from, to), false);
|
|
840
1265
|
}
|
|
841
|
-
|
|
842
|
-
exports.ImmutableSparseBits2 = ImmutableSparseBits2;
|
|
843
|
-
class SparseBits2 extends ImmutableSparseBits2 {
|
|
1266
|
+
//mutating methods
|
|
844
1267
|
set(a) {
|
|
845
1268
|
sparseSetMask(this.bits, a >> 5, 1 << (a & 0x1f), this.undef);
|
|
846
1269
|
}
|
|
@@ -856,8 +1279,8 @@ class SparseBits2 extends ImmutableSparseBits2 {
|
|
|
856
1279
|
return this;
|
|
857
1280
|
}
|
|
858
1281
|
selfComplement() {
|
|
859
|
-
this.undef = ~this.undef;
|
|
860
1282
|
sparseSelfComplement(this.bits);
|
|
1283
|
+
this.undef = ~this.undef;
|
|
861
1284
|
return this;
|
|
862
1285
|
}
|
|
863
1286
|
selfIntersect(other) {
|
|
@@ -866,6 +1289,9 @@ class SparseBits2 extends ImmutableSparseBits2 {
|
|
|
866
1289
|
sparseCopyUndefined(this.bits, other.bits);
|
|
867
1290
|
this.undef = other.undef;
|
|
868
1291
|
}
|
|
1292
|
+
else if (!other.undef) {
|
|
1293
|
+
sparseDeleteUndefined(this.bits, other.bits);
|
|
1294
|
+
}
|
|
869
1295
|
return this;
|
|
870
1296
|
}
|
|
871
1297
|
selfUnion(other) {
|
|
@@ -874,6 +1300,9 @@ class SparseBits2 extends ImmutableSparseBits2 {
|
|
|
874
1300
|
sparseCopyUndefined(this.bits, other.bits);
|
|
875
1301
|
this.undef = other.undef;
|
|
876
1302
|
}
|
|
1303
|
+
else if (other.undef) {
|
|
1304
|
+
sparseDeleteUndefined(this.bits, other.bits);
|
|
1305
|
+
}
|
|
877
1306
|
return this;
|
|
878
1307
|
}
|
|
879
1308
|
selfXor(other) {
|
|
@@ -882,6 +1311,15 @@ class SparseBits2 extends ImmutableSparseBits2 {
|
|
|
882
1311
|
this.undef ^= other.undef;
|
|
883
1312
|
return this;
|
|
884
1313
|
}
|
|
1314
|
+
selfDifference(other) {
|
|
1315
|
+
sparseSelfDifference(this.bits, other.bits);
|
|
1316
|
+
if (other.undef) {
|
|
1317
|
+
if (this.undef)
|
|
1318
|
+
sparseCopyUndefined(this.bits, other.bits, -1);
|
|
1319
|
+
this.undef = 0;
|
|
1320
|
+
}
|
|
1321
|
+
return this;
|
|
1322
|
+
}
|
|
885
1323
|
}
|
|
886
1324
|
exports.SparseBits2 = SparseBits2;
|
|
887
1325
|
;
|