Last active
January 13, 2025 15:29
-
-
Save jessealama/6497868587079a258575a2485f17fb21 to your computer and use it in GitHub Desktop.
A first stab at combining measure, decimal, and normalized decimal data types
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
export declare class Decimal128 { | |
constructor(value: string | number | bigint | NormalizedDecimal128); | |
// predicates | |
isFinite(): boolean; | |
isNegative(): boolean; | |
isNaN(): boolean; | |
isZero(): boolean; | |
// comparison | |
equals(other: Decimal128): boolean; // mathematical equality | |
lessThan(other: Decimal128): boolean; | |
// serialization | |
toJSON(): string; | |
toString(): string; | |
toFixed(opts?: {digits?: number}): string; | |
toLocaleString(locale?: string): string; | |
toPrecision(opts?: {digits?: number}): string; | |
// no arithmetic | |
// no rounding | |
// conversion | |
toNumber(): number; | |
toBigInt(): bigint; | |
toNormalizedDecimal(): NormalizedDecimal128; // or just "normalize"? | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
type ExpandedNumber = string // digit strings, not arbitrary strings | |
| number | |
| bigint | |
| Decimal128 | |
| NormalizedDecimal128; | |
export declare class Measure { | |
constructor(value: ExpandedNumber, unit?: string, precision?: number); | |
convertTo(unit: string, precision?: number): Measure; | |
toString(): string; | |
toComponents(): {value: ExpandedNumber, unit: string}[]; | |
getValue(): Decimal128; | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
export declare class NormalizedDecimal128 { // or just "Decimal"? | |
constructor(x: string | number | bigint | Decimal128); | |
// predicates | |
isFinite(): boolean; | |
isNegative(): boolean; | |
isNaN(): boolean; | |
isZero(): boolean; | |
// comparison | |
equals(other: NormalizedDecimal128): boolean; | |
lessThan(other: NormalizedDecimal128): boolean; | |
// arithmetic | |
abs(): NormalizedDecimal128; | |
add(x: NormalizedDecimal128): NormalizedDecimal128; | |
divide(x: NormalizedDecimal128): NormalizedDecimal128; | |
multiply(x: NormalizedDecimal128): NormalizedDecimal128; | |
negate(): NormalizedDecimal128; | |
subtract(x: NormalizedDecimal128): NormalizedDecimal128; | |
// serlialization | |
toJSON(): string; | |
toString(): string; | |
toFixed(opts?: {digits?: number}): string; | |
toLocaleString(locale?: string): string; | |
toPrecision(opts?: {digits?: number}): string; | |
// rounding | |
round(numFractionalDigits: number, mode: RoundingMode): NormalizedDecimal128; | |
// conversion | |
toDecimal128(): Decimal128; | |
toNumber(): number; | |
toBigInt(): bigint; | |
} |
The dividing line between 262 and 402 here could be that Measure could exist in 262 but only supports the dimensionless unit (trying to use any other unit would throw). toLocaleString
would exist in both decimal classes but would be supported in 402 only.
the absence of arithmetic support in the Decimal128 class reflects two discussions:
- the main driver for support for full Decimal128 comes mainly from i18n use cases, where arithmetic needs seem to be largely absent. I've kept
equals
andlessThan
in there, but perhaps those could also be dropped (or maybelessThan
, keepingequals
). - the lack of a good theory for what the rules for quantum preservation should be for this class of values
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
This gist sketches one possible approach in which the measure and decimal prposals are combined. Here we have three classes:
Decimal128
, for "full" IEEE 754 Decimal128, but with no arithmeticNormalizedDecimal128
for the subset of Decimal128 consisting only of normalized mathematical valuesMeasure
, offering up basics, but allowing the possibility of getting the underlying value as a (non-normalized) Decimal128.The intention is to try to keep conversions explicit, with each class sticking to its own division of responsibility.