binary-structures-values 0.1.0 → 0.1.1
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/cjs/bit-stream-reader.d.ts +1 -0
- package/dist/cjs/bit-stream-reader.js +26 -0
- package/dist/cjs/bit-stream-writer.d.ts +1 -0
- package/dist/cjs/bit-stream-writer.js +33 -0
- package/dist/esm/bit-stream-reader.d.ts +1 -0
- package/dist/esm/bit-stream-reader.js +26 -0
- package/dist/esm/bit-stream-writer.d.ts +1 -0
- package/dist/esm/bit-stream-writer.js +33 -0
- package/package.json +1 -1
|
@@ -227,6 +227,32 @@ class BitStreamReader {
|
|
|
227
227
|
this.bitPosition = currentBitPos;
|
|
228
228
|
return (result & 1n) === 0n ? result >> 1n : -((result + 1n) >> 1n);
|
|
229
229
|
}
|
|
230
|
+
readBigFloat() {
|
|
231
|
+
const mantissa = this.readBigInt();
|
|
232
|
+
if (mantissa === 0n)
|
|
233
|
+
return 0;
|
|
234
|
+
const exponent = this.readBigInt();
|
|
235
|
+
// Fast path for common cases
|
|
236
|
+
if (exponent === 0n) {
|
|
237
|
+
const numValue = Number(mantissa);
|
|
238
|
+
return BigInt(numValue) === mantissa ? numValue : [mantissa, exponent];
|
|
239
|
+
}
|
|
240
|
+
if (exponent > 0n) {
|
|
241
|
+
const value = mantissa * (10n ** exponent);
|
|
242
|
+
const numValue = Number(value);
|
|
243
|
+
return BigInt(numValue) === value ? numValue : [mantissa, exponent];
|
|
244
|
+
}
|
|
245
|
+
// Negative exponent
|
|
246
|
+
const denom = 10n ** (-exponent);
|
|
247
|
+
const numValue = mantissa % denom === 0n
|
|
248
|
+
? Number(mantissa / denom)
|
|
249
|
+
: Number(mantissa) / Number(denom);
|
|
250
|
+
// Exact check via reconstruction
|
|
251
|
+
return (Number.isFinite(numValue) &&
|
|
252
|
+
BigInt(Math.round(numValue * Number(denom))) === mantissa)
|
|
253
|
+
? numValue
|
|
254
|
+
: [mantissa, exponent];
|
|
255
|
+
}
|
|
230
256
|
readFloat32() {
|
|
231
257
|
const data = this.byteArray;
|
|
232
258
|
let pos = this.bitPosition;
|
|
@@ -22,6 +22,7 @@ export declare class BitStreamWriter {
|
|
|
22
22
|
writeInt16(value: number): void;
|
|
23
23
|
writeInt32(value: number): void;
|
|
24
24
|
writeBigInt(value: bigint): void;
|
|
25
|
+
writeBigFloat(value: number | string | [bigint, bigint] | [number, bigint] | [number, number]): void;
|
|
25
26
|
dumpBytes(label: string, bytes: Uint8Array): void;
|
|
26
27
|
writeFloat32(value: number): void;
|
|
27
28
|
writeFloat64(value: number): void;
|
|
@@ -208,6 +208,39 @@ class BitStreamWriter {
|
|
|
208
208
|
} while (val !== 0n);
|
|
209
209
|
this.bitPosition = currentBitPos;
|
|
210
210
|
}
|
|
211
|
+
writeBigFloat(value) {
|
|
212
|
+
// slightly slower
|
|
213
|
+
let mantissa;
|
|
214
|
+
let exponent;
|
|
215
|
+
if (typeof value === 'number') {
|
|
216
|
+
const str = value.toExponential();
|
|
217
|
+
const match = str.match(/^(-?)(\d+\.?\d*)e([+-]?\d+)$/);
|
|
218
|
+
if (!match)
|
|
219
|
+
throw new Error(`Invalid number format: ${str}`);
|
|
220
|
+
const [, sign, man, exp] = match;
|
|
221
|
+
mantissa = BigInt(sign + man.replace('.', ''));
|
|
222
|
+
exponent = BigInt(parseInt(exp) - (man.includes('.') ? man.split('.')[1].length : 0));
|
|
223
|
+
}
|
|
224
|
+
else if (typeof value === 'string') {
|
|
225
|
+
const match = value.match(/^(-?)(\d+)\.(\d+)$/);
|
|
226
|
+
if (!match)
|
|
227
|
+
throw new Error(`Invalid string number format, expected decimal like 123.456: ${value}`);
|
|
228
|
+
const [, sign, intPart, fracPart] = match;
|
|
229
|
+
const mantissaStr = sign + intPart + fracPart;
|
|
230
|
+
exponent = BigInt(-fracPart.length);
|
|
231
|
+
mantissa = BigInt(mantissaStr);
|
|
232
|
+
}
|
|
233
|
+
else if (Array.isArray(value)) {
|
|
234
|
+
const [man, exp] = value;
|
|
235
|
+
mantissa = typeof man === 'bigint' ? man : BigInt(man);
|
|
236
|
+
exponent = typeof exp === 'bigint' ? exp : BigInt(exp);
|
|
237
|
+
}
|
|
238
|
+
else {
|
|
239
|
+
throw new Error(`Unsupported value type for writeBigFloat: ${typeof value}`);
|
|
240
|
+
}
|
|
241
|
+
this.writeBigInt(mantissa);
|
|
242
|
+
this.writeBigInt(exponent);
|
|
243
|
+
}
|
|
211
244
|
dumpBytes(label, bytes) {
|
|
212
245
|
console.log(label, Array.from(bytes).map(b => b.toString(2).padStart(8, '0')).join(' '));
|
|
213
246
|
}
|
|
@@ -224,6 +224,32 @@ export class BitStreamReader {
|
|
|
224
224
|
this.bitPosition = currentBitPos;
|
|
225
225
|
return (result & 1n) === 0n ? result >> 1n : -((result + 1n) >> 1n);
|
|
226
226
|
}
|
|
227
|
+
readBigFloat() {
|
|
228
|
+
const mantissa = this.readBigInt();
|
|
229
|
+
if (mantissa === 0n)
|
|
230
|
+
return 0;
|
|
231
|
+
const exponent = this.readBigInt();
|
|
232
|
+
// Fast path for common cases
|
|
233
|
+
if (exponent === 0n) {
|
|
234
|
+
const numValue = Number(mantissa);
|
|
235
|
+
return BigInt(numValue) === mantissa ? numValue : [mantissa, exponent];
|
|
236
|
+
}
|
|
237
|
+
if (exponent > 0n) {
|
|
238
|
+
const value = mantissa * (10n ** exponent);
|
|
239
|
+
const numValue = Number(value);
|
|
240
|
+
return BigInt(numValue) === value ? numValue : [mantissa, exponent];
|
|
241
|
+
}
|
|
242
|
+
// Negative exponent
|
|
243
|
+
const denom = 10n ** (-exponent);
|
|
244
|
+
const numValue = mantissa % denom === 0n
|
|
245
|
+
? Number(mantissa / denom)
|
|
246
|
+
: Number(mantissa) / Number(denom);
|
|
247
|
+
// Exact check via reconstruction
|
|
248
|
+
return (Number.isFinite(numValue) &&
|
|
249
|
+
BigInt(Math.round(numValue * Number(denom))) === mantissa)
|
|
250
|
+
? numValue
|
|
251
|
+
: [mantissa, exponent];
|
|
252
|
+
}
|
|
227
253
|
readFloat32() {
|
|
228
254
|
const data = this.byteArray;
|
|
229
255
|
let pos = this.bitPosition;
|
|
@@ -22,6 +22,7 @@ export declare class BitStreamWriter {
|
|
|
22
22
|
writeInt16(value: number): void;
|
|
23
23
|
writeInt32(value: number): void;
|
|
24
24
|
writeBigInt(value: bigint): void;
|
|
25
|
+
writeBigFloat(value: number | string | [bigint, bigint] | [number, bigint] | [number, number]): void;
|
|
25
26
|
dumpBytes(label: string, bytes: Uint8Array): void;
|
|
26
27
|
writeFloat32(value: number): void;
|
|
27
28
|
writeFloat64(value: number): void;
|
|
@@ -209,6 +209,39 @@ export class BitStreamWriter {
|
|
|
209
209
|
} while (val !== 0n);
|
|
210
210
|
this.bitPosition = currentBitPos;
|
|
211
211
|
}
|
|
212
|
+
writeBigFloat(value) {
|
|
213
|
+
// slightly slower
|
|
214
|
+
let mantissa;
|
|
215
|
+
let exponent;
|
|
216
|
+
if (typeof value === 'number') {
|
|
217
|
+
const str = value.toExponential();
|
|
218
|
+
const match = str.match(/^(-?)(\d+\.?\d*)e([+-]?\d+)$/);
|
|
219
|
+
if (!match)
|
|
220
|
+
throw new Error(`Invalid number format: ${str}`);
|
|
221
|
+
const [, sign, man, exp] = match;
|
|
222
|
+
mantissa = BigInt(sign + man.replace('.', ''));
|
|
223
|
+
exponent = BigInt(parseInt(exp) - (man.includes('.') ? man.split('.')[1].length : 0));
|
|
224
|
+
}
|
|
225
|
+
else if (typeof value === 'string') {
|
|
226
|
+
const match = value.match(/^(-?)(\d+)\.(\d+)$/);
|
|
227
|
+
if (!match)
|
|
228
|
+
throw new Error(`Invalid string number format, expected decimal like 123.456: ${value}`);
|
|
229
|
+
const [, sign, intPart, fracPart] = match;
|
|
230
|
+
const mantissaStr = sign + intPart + fracPart;
|
|
231
|
+
exponent = BigInt(-fracPart.length);
|
|
232
|
+
mantissa = BigInt(mantissaStr);
|
|
233
|
+
}
|
|
234
|
+
else if (Array.isArray(value)) {
|
|
235
|
+
const [man, exp] = value;
|
|
236
|
+
mantissa = typeof man === 'bigint' ? man : BigInt(man);
|
|
237
|
+
exponent = typeof exp === 'bigint' ? exp : BigInt(exp);
|
|
238
|
+
}
|
|
239
|
+
else {
|
|
240
|
+
throw new Error(`Unsupported value type for writeBigFloat: ${typeof value}`);
|
|
241
|
+
}
|
|
242
|
+
this.writeBigInt(mantissa);
|
|
243
|
+
this.writeBigInt(exponent);
|
|
244
|
+
}
|
|
212
245
|
dumpBytes(label, bytes) {
|
|
213
246
|
console.log(label, Array.from(bytes).map(b => b.toString(2).padStart(8, '0')).join(' '));
|
|
214
247
|
}
|