@keplr-wallet/unit 0.9.10 → 0.9.12-rc.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/build/coin-pretty.d.ts +13 -3
- package/build/coin-pretty.js +36 -25
- package/build/coin-pretty.js.map +1 -1
- package/build/coin-pretty.spec.js +194 -9
- package/build/coin-pretty.spec.js.map +1 -1
- package/build/coin-utils.js +8 -4
- package/build/coin-utils.js.map +1 -1
- package/build/coin-utils.spec.js +16 -0
- package/build/coin-utils.spec.js.map +1 -1
- package/build/coin.js +1 -1
- package/build/coin.js.map +1 -1
- package/build/coin.spec.js +15 -0
- package/build/coin.spec.js.map +1 -1
- package/build/dec-utils.d.ts +8 -1
- package/build/dec-utils.js +22 -20
- package/build/dec-utils.js.map +1 -1
- package/build/dec-utils.spec.js +19 -0
- package/build/dec-utils.spec.js.map +1 -1
- package/build/decimal.d.ts +22 -9
- package/build/decimal.js +102 -29
- package/build/decimal.js.map +1 -1
- package/build/decimal.spec.js +296 -3
- package/build/decimal.spec.js.map +1 -1
- package/build/etc.d.ts +4 -0
- package/build/etc.js +66 -0
- package/build/etc.js.map +1 -0
- package/build/etc.spec.d.ts +1 -0
- package/build/etc.spec.js +66 -0
- package/build/etc.spec.js.map +1 -0
- package/build/index.d.ts +1 -0
- package/build/index.js +1 -0
- package/build/index.js.map +1 -1
- package/build/int-pretty.d.ts +16 -4
- package/build/int-pretty.js +74 -36
- package/build/int-pretty.js.map +1 -1
- package/build/int-pretty.spec.js +261 -94
- package/build/int-pretty.spec.js.map +1 -1
- package/build/int.d.ts +17 -12
- package/build/int.js +69 -16
- package/build/int.js.map +1 -1
- package/build/int.spec.d.ts +1 -0
- package/build/int.spec.js +161 -0
- package/build/int.spec.js.map +1 -0
- package/build/price-pretty.d.ts +13 -3
- package/build/price-pretty.js +37 -26
- package/build/price-pretty.js.map +1 -1
- package/build/price-pretty.spec.js +59 -2
- package/build/price-pretty.spec.js.map +1 -1
- package/build/rate-pretty.d.ts +57 -0
- package/build/rate-pretty.js +128 -0
- package/build/rate-pretty.js.map +1 -0
- package/build/rate-pretty.spec.d.ts +1 -0
- package/build/rate-pretty.spec.js +38 -0
- package/build/rate-pretty.spec.js.map +1 -0
- package/package.json +3 -3
- package/src/coin-pretty.spec.ts +304 -11
- package/src/coin-pretty.ts +56 -29
- package/src/coin-utils.spec.ts +32 -0
- package/src/coin-utils.ts +12 -4
- package/src/coin.spec.ts +20 -0
- package/src/coin.ts +1 -1
- package/src/dec-utils.spec.ts +39 -0
- package/src/dec-utils.ts +25 -20
- package/src/decimal.spec.ts +361 -3
- package/src/decimal.ts +135 -56
- package/src/etc.spec.ts +73 -0
- package/src/etc.ts +73 -0
- package/src/index.ts +1 -0
- package/src/int-pretty.spec.ts +296 -101
- package/src/int-pretty.ts +87 -34
- package/src/int.spec.ts +212 -0
- package/src/int.ts +94 -26
- package/src/price-pretty.spec.ts +106 -2
- package/src/price-pretty.ts +50 -30
- package/src/rate-pretty.spec.ts +52 -0
- package/src/rate-pretty.ts +165 -0
package/src/int-pretty.ts
CHANGED
@@ -3,35 +3,41 @@ import { Dec } from "./decimal";
|
|
3
3
|
import { DecUtils } from "./dec-utils";
|
4
4
|
import { CoinUtils } from "./coin-utils";
|
5
5
|
import { DeepReadonly } from "utility-types";
|
6
|
+
import bigInteger from "big-integer";
|
6
7
|
|
7
8
|
export type IntPrettyOptions = {
|
8
|
-
precision: number;
|
9
9
|
maxDecimals: number;
|
10
10
|
trim: boolean;
|
11
11
|
shrink: boolean;
|
12
12
|
ready: boolean;
|
13
13
|
locale: boolean;
|
14
|
+
// If this is true, toString() will return the string with prefix like < 0.001 if a value cannot be expressed with a max decimals.
|
15
|
+
inequalitySymbol: boolean;
|
16
|
+
inequalitySymbolSeparator: string;
|
14
17
|
};
|
15
18
|
|
16
19
|
export class IntPretty {
|
17
20
|
protected dec: Dec;
|
18
|
-
protected
|
21
|
+
protected floatingDecimalPointRight = 0;
|
19
22
|
|
20
23
|
protected _options: IntPrettyOptions = {
|
21
|
-
precision: 0,
|
22
24
|
maxDecimals: 0,
|
23
25
|
trim: false,
|
24
26
|
shrink: false,
|
25
27
|
ready: true,
|
26
28
|
locale: true,
|
29
|
+
inequalitySymbol: false,
|
30
|
+
inequalitySymbolSeparator: " ",
|
27
31
|
};
|
28
32
|
|
29
|
-
constructor(num: Dec | { toDec(): Dec }) {
|
30
|
-
if ("toDec" in num) {
|
33
|
+
constructor(num: Dec | { toDec(): Dec } | bigInteger.BigNumber) {
|
34
|
+
if (typeof num === "object" && "toDec" in num) {
|
31
35
|
num = num.toDec();
|
36
|
+
} else if (!(num instanceof Dec)) {
|
37
|
+
num = new Dec(num);
|
32
38
|
}
|
33
39
|
|
34
|
-
if (num.
|
40
|
+
if (num.isZero()) {
|
35
41
|
this.dec = num;
|
36
42
|
return;
|
37
43
|
}
|
@@ -50,8 +56,6 @@ export class IntPretty {
|
|
50
56
|
}
|
51
57
|
|
52
58
|
this.dec = num;
|
53
|
-
this.decPrecision = decPrecision;
|
54
|
-
this._options.precision = decPrecision;
|
55
59
|
this._options.maxDecimals = decPrecision;
|
56
60
|
}
|
57
61
|
|
@@ -59,25 +63,30 @@ export class IntPretty {
|
|
59
63
|
return this._options;
|
60
64
|
}
|
61
65
|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
throw new Error("Too much precision");
|
68
|
-
}
|
66
|
+
moveDecimalPointLeft(delta: number): IntPretty {
|
67
|
+
const pretty = this.clone();
|
68
|
+
pretty.floatingDecimalPointRight += -delta;
|
69
|
+
return pretty;
|
70
|
+
}
|
69
71
|
|
72
|
+
moveDecimalPointRight(delta: number): IntPretty {
|
70
73
|
const pretty = this.clone();
|
71
|
-
pretty.
|
74
|
+
pretty.floatingDecimalPointRight += delta;
|
72
75
|
return pretty;
|
73
76
|
}
|
74
77
|
|
78
|
+
/**
|
79
|
+
* @deprecated Use`moveDecimalPointLeft`
|
80
|
+
*/
|
75
81
|
increasePrecision(delta: number): IntPretty {
|
76
|
-
return this.
|
82
|
+
return this.moveDecimalPointLeft(delta);
|
77
83
|
}
|
78
84
|
|
85
|
+
/**
|
86
|
+
* @deprecated Use`moveDecimalPointRight`
|
87
|
+
*/
|
79
88
|
decreasePrecision(delta: number): IntPretty {
|
80
|
-
return this.
|
89
|
+
return this.moveDecimalPointRight(delta);
|
81
90
|
}
|
82
91
|
|
83
92
|
maxDecimals(max: number): IntPretty {
|
@@ -86,6 +95,18 @@ export class IntPretty {
|
|
86
95
|
return pretty;
|
87
96
|
}
|
88
97
|
|
98
|
+
inequalitySymbol(bool: boolean): IntPretty {
|
99
|
+
const pretty = this.clone();
|
100
|
+
pretty._options.inequalitySymbol = bool;
|
101
|
+
return pretty;
|
102
|
+
}
|
103
|
+
|
104
|
+
inequalitySymbolSeparator(str: string): IntPretty {
|
105
|
+
const pretty = this.clone();
|
106
|
+
pretty._options.inequalitySymbolSeparator = str;
|
107
|
+
return pretty;
|
108
|
+
}
|
109
|
+
|
89
110
|
trim(bool: boolean): IntPretty {
|
90
111
|
const pretty = this.clone();
|
91
112
|
pretty._options.trim = bool;
|
@@ -129,8 +150,6 @@ export class IntPretty {
|
|
129
150
|
const pretty = new IntPretty(this.toDec().add(target));
|
130
151
|
pretty._options = {
|
131
152
|
...this._options,
|
132
|
-
// Precision must not be changed.
|
133
|
-
precision: pretty._options.precision,
|
134
153
|
};
|
135
154
|
return pretty;
|
136
155
|
}
|
@@ -143,8 +162,6 @@ export class IntPretty {
|
|
143
162
|
const pretty = new IntPretty(this.toDec().sub(target));
|
144
163
|
pretty._options = {
|
145
164
|
...this._options,
|
146
|
-
// Precision must not be changed.
|
147
|
-
precision: pretty._options.precision,
|
148
165
|
};
|
149
166
|
return pretty;
|
150
167
|
}
|
@@ -157,8 +174,6 @@ export class IntPretty {
|
|
157
174
|
const pretty = new IntPretty(this.toDec().mul(target));
|
158
175
|
pretty._options = {
|
159
176
|
...this._options,
|
160
|
-
// Precision must not be changed.
|
161
|
-
precision: pretty._options.precision,
|
162
177
|
};
|
163
178
|
return pretty;
|
164
179
|
}
|
@@ -171,25 +186,57 @@ export class IntPretty {
|
|
171
186
|
const pretty = new IntPretty(this.toDec().quo(target));
|
172
187
|
pretty._options = {
|
173
188
|
...this._options,
|
174
|
-
// Precision must not be changed.
|
175
|
-
precision: pretty._options.precision,
|
176
189
|
};
|
177
190
|
return pretty;
|
178
191
|
}
|
179
192
|
|
180
193
|
toDec(): Dec {
|
181
|
-
|
182
|
-
|
183
|
-
if (
|
184
|
-
|
194
|
+
if (this.floatingDecimalPointRight === 0) {
|
195
|
+
return this.dec;
|
196
|
+
} else if (this.floatingDecimalPointRight > 0) {
|
197
|
+
return this.dec.mulTruncate(
|
198
|
+
DecUtils.getTenExponentN(this.floatingDecimalPointRight)
|
199
|
+
);
|
200
|
+
} else {
|
201
|
+
// Since a decimal in Dec cannot exceed 18, it cannot be computed at once.
|
202
|
+
let i = -this.floatingDecimalPointRight;
|
203
|
+
let dec = this.dec;
|
204
|
+
while (i > 0) {
|
205
|
+
if (i >= Dec.precision) {
|
206
|
+
dec = dec.mulTruncate(DecUtils.getTenExponentN(-Dec.precision));
|
207
|
+
i -= Dec.precision;
|
208
|
+
} else {
|
209
|
+
dec = dec.mulTruncate(DecUtils.getTenExponentN(-(i % Dec.precision)));
|
210
|
+
break;
|
211
|
+
}
|
212
|
+
}
|
213
|
+
return dec;
|
185
214
|
}
|
186
|
-
return dec;
|
187
215
|
}
|
188
216
|
|
189
217
|
toString(): string {
|
218
|
+
return this.toStringWithSymbols("", "");
|
219
|
+
}
|
220
|
+
|
221
|
+
toStringWithSymbols(prefix: string, suffix: string): string {
|
190
222
|
const dec = this.toDec();
|
191
223
|
|
192
|
-
|
224
|
+
if (
|
225
|
+
this._options.inequalitySymbol &&
|
226
|
+
!dec.isZero() &&
|
227
|
+
dec.abs().lt(DecUtils.getTenExponentN(-this._options.maxDecimals))
|
228
|
+
) {
|
229
|
+
const isNeg = dec.isNegative();
|
230
|
+
|
231
|
+
return `${isNeg ? ">" : "<"}${this._options.inequalitySymbolSeparator}${
|
232
|
+
isNeg ? "-" : ""
|
233
|
+
}${prefix}${DecUtils.getTenExponentN(-this._options.maxDecimals).toString(
|
234
|
+
this._options.maxDecimals,
|
235
|
+
this._options.locale
|
236
|
+
)}${suffix}`;
|
237
|
+
}
|
238
|
+
|
239
|
+
let result: string;
|
193
240
|
if (!this._options.shrink) {
|
194
241
|
result = dec.toString(this._options.maxDecimals, this._options.locale);
|
195
242
|
} else {
|
@@ -203,13 +250,19 @@ export class IntPretty {
|
|
203
250
|
if (this._options.trim) {
|
204
251
|
result = DecUtils.trim(result);
|
205
252
|
}
|
206
|
-
|
253
|
+
|
254
|
+
const isNeg = result.charAt(0) === "-";
|
255
|
+
if (isNeg) {
|
256
|
+
result = result.slice(1);
|
257
|
+
}
|
258
|
+
|
259
|
+
return `${isNeg ? "-" : ""}${prefix}${result}${suffix}`;
|
207
260
|
}
|
208
261
|
|
209
262
|
clone(): IntPretty {
|
210
263
|
const pretty = new IntPretty(this.dec);
|
211
264
|
pretty.dec = this.dec;
|
212
|
-
pretty.
|
265
|
+
pretty.floatingDecimalPointRight = this.floatingDecimalPointRight;
|
213
266
|
pretty._options = {
|
214
267
|
...this._options,
|
215
268
|
};
|
package/src/int.spec.ts
ADDED
@@ -0,0 +1,212 @@
|
|
1
|
+
import { Int, Uint } from "./int";
|
2
|
+
import { Dec } from "./decimal";
|
3
|
+
|
4
|
+
describe("Test Int/Uint", () => {
|
5
|
+
// (2 ** 256) - 1
|
6
|
+
const maxInt =
|
7
|
+
"115792089237316195423570985008687907853269984665640564039457584007913129639935";
|
8
|
+
// 2 ** 256
|
9
|
+
const overflowedInt =
|
10
|
+
"115792089237316195423570985008687907853269984665640564039457584007913129639936";
|
11
|
+
|
12
|
+
it("Test parsing Int", () => {
|
13
|
+
expect(new Int(0).toString()).toBe("0");
|
14
|
+
expect(new Int(-0).toString()).toBe("0");
|
15
|
+
expect(new Int(1).toString()).toBe("1");
|
16
|
+
expect(new Int(-1).toString()).toBe("-1");
|
17
|
+
expect(new Int("-123").toString()).toBe("-123");
|
18
|
+
|
19
|
+
expect(new Int(maxInt).toString()).toBe(maxInt);
|
20
|
+
expect(new Int("-" + maxInt).toString()).toBe("-" + maxInt);
|
21
|
+
|
22
|
+
expect(() => new Int("1.1")).toThrow();
|
23
|
+
expect(() => new Int("1.0")).toThrow();
|
24
|
+
expect(() => new Int(1.1)).toThrow();
|
25
|
+
expect(() => new Int("-1.1")).toThrow();
|
26
|
+
|
27
|
+
expect(() => new Int("str")).toThrow();
|
28
|
+
});
|
29
|
+
|
30
|
+
it("Test Int/Uint toDec", () => {
|
31
|
+
expect(new Int(0).toDec().toString()).toBe(new Dec(0).toString());
|
32
|
+
expect(new Uint(0).toDec().toString()).toBe(new Dec(0).toString());
|
33
|
+
|
34
|
+
expect(new Int(123).toDec().toString()).toBe(new Dec(123).toString());
|
35
|
+
expect(new Uint(123).toDec().toString()).toBe(new Dec(123).toString());
|
36
|
+
|
37
|
+
expect(new Int(-123).toDec().toString()).toBe(new Dec(-123).toString());
|
38
|
+
});
|
39
|
+
|
40
|
+
it("Test Int/Uint overflow", () => {
|
41
|
+
expect(() => new Int(overflowedInt)).toThrow();
|
42
|
+
expect(() => new Int("-" + overflowedInt)).toThrow();
|
43
|
+
|
44
|
+
const max = new Int(maxInt);
|
45
|
+
expect(() => max.add(new Int(1))).toThrow();
|
46
|
+
const min = new Int("-" + maxInt);
|
47
|
+
expect(() => min.sub(new Int(1))).toThrow();
|
48
|
+
|
49
|
+
expect(() => new Uint(overflowedInt)).toThrow();
|
50
|
+
const uMax = new Uint(maxInt);
|
51
|
+
expect(() => uMax.add(new Uint(1))).toThrow();
|
52
|
+
});
|
53
|
+
|
54
|
+
it("Test parsing UInt", () => {
|
55
|
+
expect(new Uint(0).toString()).toBe("0");
|
56
|
+
expect(new Uint(-0).toString()).toBe("0");
|
57
|
+
expect(new Uint(1).toString()).toBe("1");
|
58
|
+
|
59
|
+
expect(new Uint(maxInt).toString()).toBe(maxInt);
|
60
|
+
|
61
|
+
expect(() => new Uint("1.1")).toThrow();
|
62
|
+
expect(() => new Uint("1.0")).toThrow();
|
63
|
+
expect(() => new Uint(1.1)).toThrow();
|
64
|
+
expect(() => new Uint("-1.1")).toThrow();
|
65
|
+
|
66
|
+
expect(() => new Uint("str")).toThrow();
|
67
|
+
});
|
68
|
+
|
69
|
+
it("Test UInt overflow", () => {
|
70
|
+
expect(() => new Int(overflowedInt)).toThrow();
|
71
|
+
|
72
|
+
const max = new Int(maxInt);
|
73
|
+
expect(() => max.add(new Int(1))).toThrow();
|
74
|
+
});
|
75
|
+
|
76
|
+
it("Test Uint can not be negative", () => {
|
77
|
+
expect(() => new Uint(-1)).toThrow();
|
78
|
+
expect(() => new Uint("-123")).toThrow();
|
79
|
+
|
80
|
+
const uint = new Uint(0);
|
81
|
+
expect(() => uint.sub(new Uint(1))).toThrow();
|
82
|
+
});
|
83
|
+
|
84
|
+
it("Test Int isNegative/isPositive/isZero", () => {
|
85
|
+
expect(new Int(1).isPositive()).toBe(true);
|
86
|
+
expect(new Int(1).isNegative()).toBe(false);
|
87
|
+
|
88
|
+
expect(new Int(-1).isPositive()).toBe(false);
|
89
|
+
expect(new Int(-1).isNegative()).toBe(true);
|
90
|
+
|
91
|
+
expect(new Int(0).isZero()).toBe(true);
|
92
|
+
expect(new Int(1).isZero()).toBe(false);
|
93
|
+
expect(new Int(-1).isZero()).toBe(false);
|
94
|
+
});
|
95
|
+
|
96
|
+
it("Test Uint isZero", () => {
|
97
|
+
expect(new Uint(0).isZero()).toBe(true);
|
98
|
+
expect(new Uint(1).isZero()).toBe(false);
|
99
|
+
});
|
100
|
+
|
101
|
+
it("Test Int computation", () => {
|
102
|
+
const int1 = new Int(1);
|
103
|
+
const int2 = new Int(2);
|
104
|
+
const int3 = new Int(3);
|
105
|
+
|
106
|
+
expect(int1.add(int2).toString()).toBe("3");
|
107
|
+
|
108
|
+
expect(int1.sub(int2).toString()).toBe("-1");
|
109
|
+
expect(int2.sub(int1).toString()).toBe("1");
|
110
|
+
|
111
|
+
expect(int1.mul(int2).toString()).toBe("2");
|
112
|
+
|
113
|
+
expect(int1.div(int2).toString()).toBe("0");
|
114
|
+
expect(int2.div(int1).toString()).toBe("2");
|
115
|
+
expect(int3.div(int2).toString()).toBe("1");
|
116
|
+
|
117
|
+
expect(int1.mod(int2).toString()).toBe("1");
|
118
|
+
expect(int2.mod(int1).toString()).toBe("0");
|
119
|
+
expect(int3.mod(int2).toString()).toBe("1");
|
120
|
+
|
121
|
+
expect(int1.neg().toString()).toBe("-1");
|
122
|
+
expect(int1.neg().abs().toString()).toBe("1");
|
123
|
+
expect(int1.neg().absUInt().toString()).toBe("1");
|
124
|
+
|
125
|
+
expect(int1.pow(int3.absUInt()).toString()).toBe("1");
|
126
|
+
expect(int2.pow(int3.absUInt()).toString()).toBe("8");
|
127
|
+
});
|
128
|
+
|
129
|
+
it("Test Uint computation", () => {
|
130
|
+
const int1 = new Uint(1);
|
131
|
+
const int2 = new Uint(2);
|
132
|
+
const int3 = new Uint(3);
|
133
|
+
|
134
|
+
expect(int1.add(int2).toString()).toBe("3");
|
135
|
+
|
136
|
+
expect(() => int1.sub(int2).toString()).toThrow();
|
137
|
+
expect(int2.sub(int1).toString()).toBe("1");
|
138
|
+
|
139
|
+
expect(int1.mul(int2).toString()).toBe("2");
|
140
|
+
|
141
|
+
expect(int1.div(int2).toString()).toBe("0");
|
142
|
+
expect(int2.div(int1).toString()).toBe("2");
|
143
|
+
expect(int3.div(int2).toString()).toBe("1");
|
144
|
+
|
145
|
+
expect(int1.mod(int2).toString()).toBe("1");
|
146
|
+
expect(int2.mod(int1).toString()).toBe("0");
|
147
|
+
expect(int3.mod(int2).toString()).toBe("1");
|
148
|
+
|
149
|
+
expect(int1.pow(int3).toString()).toBe("1");
|
150
|
+
expect(int2.pow(int3).toString()).toBe("8");
|
151
|
+
});
|
152
|
+
|
153
|
+
it("Test Int/Uint comparison", () => {
|
154
|
+
const int1 = new Int(1);
|
155
|
+
const int2 = new Int(2);
|
156
|
+
|
157
|
+
expect(int1.gt(int2)).toBe(false);
|
158
|
+
expect(int1.gte(int1)).toBe(true);
|
159
|
+
|
160
|
+
expect(int1.lt(int2)).toBe(true);
|
161
|
+
expect(int1.lte(int1)).toBe(true);
|
162
|
+
|
163
|
+
expect(int1.equals(int2)).toBe(false);
|
164
|
+
expect(int1.equals(int1)).toBe(true);
|
165
|
+
|
166
|
+
const uint1 = new Uint(1);
|
167
|
+
const uint2 = new Uint(2);
|
168
|
+
|
169
|
+
expect(uint1.gt(uint2)).toBe(false);
|
170
|
+
expect(uint1.gte(uint1)).toBe(true);
|
171
|
+
|
172
|
+
expect(uint1.lt(uint2)).toBe(true);
|
173
|
+
expect(uint1.lte(uint1)).toBe(true);
|
174
|
+
|
175
|
+
expect(uint1.equals(uint2)).toBe(false);
|
176
|
+
expect(uint1.equals(uint1)).toBe(true);
|
177
|
+
});
|
178
|
+
|
179
|
+
it("Test Int/Uint from exponent number", () => {
|
180
|
+
const tests: {
|
181
|
+
num: number;
|
182
|
+
str: string;
|
183
|
+
expect: Int | Uint;
|
184
|
+
}[] = [
|
185
|
+
{
|
186
|
+
num: 12345678901234567890123,
|
187
|
+
str: "1.2345678901234568e+22",
|
188
|
+
expect: new Int("12345678901234568000000"),
|
189
|
+
},
|
190
|
+
{
|
191
|
+
num: -12345678901234567890123,
|
192
|
+
str: "-1.2345678901234568e+22",
|
193
|
+
expect: new Int("-12345678901234568000000"),
|
194
|
+
},
|
195
|
+
{
|
196
|
+
num: 12345678901234567890123,
|
197
|
+
str: "1.2345678901234568e+22",
|
198
|
+
expect: new Uint("12345678901234568000000"),
|
199
|
+
},
|
200
|
+
];
|
201
|
+
|
202
|
+
for (const test of tests) {
|
203
|
+
expect(test.num.toString()).toBe(test.str);
|
204
|
+
|
205
|
+
if (test.expect instanceof Int) {
|
206
|
+
expect(new Int(test.num).equals(test.expect)).toBe(true);
|
207
|
+
} else {
|
208
|
+
expect(new Uint(test.num).equals(test.expect)).toBe(true);
|
209
|
+
}
|
210
|
+
}
|
211
|
+
});
|
212
|
+
});
|
package/src/int.ts
CHANGED
@@ -1,37 +1,68 @@
|
|
1
1
|
import bigInteger from "big-integer";
|
2
2
|
import { Dec } from "./decimal";
|
3
|
+
import {
|
4
|
+
exponentDecStringToDecString,
|
5
|
+
isExponentDecString,
|
6
|
+
isValidIntegerString,
|
7
|
+
} from "./etc";
|
3
8
|
|
4
9
|
export class Int {
|
5
|
-
|
10
|
+
// (2 ** 256) - 1
|
11
|
+
protected static maxInt = bigInteger(
|
12
|
+
"115792089237316195423570985008687907853269984665640564039457584007913129639935"
|
13
|
+
);
|
14
|
+
|
15
|
+
protected int: bigInteger.BigInteger;
|
6
16
|
|
7
17
|
/**
|
8
18
|
* @param int - Parse a number | bigInteger | string into a bigInt.
|
9
|
-
* Remaing parameters only will be used when type of int is string.
|
10
|
-
* @param base - Default base is 10.
|
11
|
-
* @param alphabet - Default alphabet is "0123456789abcdefghijklmnopqrstuvwxyz".
|
12
|
-
* @param caseSensitive - Defaults to false.
|
13
19
|
*/
|
14
|
-
constructor(
|
15
|
-
int
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
) {
|
20
|
+
constructor(int: bigInteger.BigNumber) {
|
21
|
+
if (typeof int === "number") {
|
22
|
+
int = int.toString();
|
23
|
+
}
|
24
|
+
|
20
25
|
if (typeof int === "string") {
|
21
|
-
|
22
|
-
|
26
|
+
if (!isValidIntegerString(int)) {
|
27
|
+
if (isExponentDecString(int)) {
|
28
|
+
int = exponentDecStringToDecString(int);
|
29
|
+
} else {
|
30
|
+
throw new Error(`invalid integer: ${int}`);
|
31
|
+
}
|
32
|
+
}
|
33
|
+
|
23
34
|
this.int = bigInteger(int);
|
24
35
|
} else if (typeof int === "bigint") {
|
25
36
|
this.int = bigInteger(int);
|
26
37
|
} else {
|
27
38
|
this.int = bigInteger(int);
|
28
39
|
}
|
40
|
+
|
41
|
+
this.checkBitLen();
|
42
|
+
}
|
43
|
+
|
44
|
+
protected checkBitLen(): void {
|
45
|
+
if (this.int.abs().gt(Int.maxInt)) {
|
46
|
+
throw new Error(`Integer out of range ${this.int.toString()}`);
|
47
|
+
}
|
29
48
|
}
|
30
49
|
|
31
50
|
public toString(): string {
|
32
51
|
return this.int.toString(10);
|
33
52
|
}
|
34
53
|
|
54
|
+
public isNegative(): boolean {
|
55
|
+
return this.int.isNegative();
|
56
|
+
}
|
57
|
+
|
58
|
+
public isPositive(): boolean {
|
59
|
+
return this.int.isPositive();
|
60
|
+
}
|
61
|
+
|
62
|
+
public isZero(): boolean {
|
63
|
+
return this.int.eq(bigInteger(0));
|
64
|
+
}
|
65
|
+
|
35
66
|
public equals(i: Int): boolean {
|
36
67
|
return this.int.equals(i.int);
|
37
68
|
}
|
@@ -52,6 +83,14 @@ export class Int {
|
|
52
83
|
return this.int.lesserOrEquals(i.int);
|
53
84
|
}
|
54
85
|
|
86
|
+
public abs(): Int {
|
87
|
+
return new Int(this.int.abs());
|
88
|
+
}
|
89
|
+
|
90
|
+
public absUInt(): Uint {
|
91
|
+
return new Uint(this.int.abs());
|
92
|
+
}
|
93
|
+
|
55
94
|
public add(i: Int): Int {
|
56
95
|
return new Int(this.int.add(i.int));
|
57
96
|
}
|
@@ -76,30 +115,39 @@ export class Int {
|
|
76
115
|
return new Int(this.int.negate());
|
77
116
|
}
|
78
117
|
|
118
|
+
public pow(i: Uint): Int {
|
119
|
+
return new Int(this.int.pow(i.toBigNumber()));
|
120
|
+
}
|
121
|
+
|
79
122
|
public toDec(): Dec {
|
80
123
|
return new Dec(this);
|
81
124
|
}
|
125
|
+
|
126
|
+
public toBigNumber(): bigInteger.BigInteger {
|
127
|
+
return this.int;
|
128
|
+
}
|
82
129
|
}
|
83
130
|
|
84
131
|
export class Uint {
|
85
|
-
|
132
|
+
protected uint: bigInteger.BigInteger;
|
86
133
|
|
87
134
|
/**
|
88
135
|
* @param uint - Parse a number | bigInteger | string into a bigUint.
|
89
|
-
* Remaing parameters only will be used when type of int is string.
|
90
|
-
* @param base - Default base is 10.
|
91
|
-
* @param alphabet - Default alphabet is "0123456789abcdefghijklmnopqrstuvwxyz".
|
92
|
-
* @param caseSensitive - Defaults to false.
|
93
136
|
*/
|
94
|
-
constructor(
|
95
|
-
uint
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
) {
|
137
|
+
constructor(uint: bigInteger.BigNumber) {
|
138
|
+
if (typeof uint === "number") {
|
139
|
+
uint = uint.toString();
|
140
|
+
}
|
141
|
+
|
100
142
|
if (typeof uint === "string") {
|
101
|
-
|
102
|
-
|
143
|
+
if (!isValidIntegerString(uint)) {
|
144
|
+
if (isExponentDecString(uint)) {
|
145
|
+
uint = exponentDecStringToDecString(uint);
|
146
|
+
} else {
|
147
|
+
throw new Error(`invalid integer: ${uint}`);
|
148
|
+
}
|
149
|
+
}
|
150
|
+
|
103
151
|
this.uint = bigInteger(uint);
|
104
152
|
} else if (typeof uint === "bigint") {
|
105
153
|
this.uint = bigInteger(uint);
|
@@ -110,12 +158,24 @@ export class Uint {
|
|
110
158
|
if (this.uint.isNegative()) {
|
111
159
|
throw new TypeError("Uint should not be negative");
|
112
160
|
}
|
161
|
+
|
162
|
+
this.checkBitLen();
|
163
|
+
}
|
164
|
+
|
165
|
+
protected checkBitLen(): void {
|
166
|
+
if (this.uint.abs().bitLength().gt(256)) {
|
167
|
+
throw new Error(`Integer out of range ${this.uint.toString()}`);
|
168
|
+
}
|
113
169
|
}
|
114
170
|
|
115
171
|
public toString(): string {
|
116
172
|
return this.uint.toString(10);
|
117
173
|
}
|
118
174
|
|
175
|
+
public isZero(): boolean {
|
176
|
+
return this.uint.eq(bigInteger(0));
|
177
|
+
}
|
178
|
+
|
119
179
|
public equals(i: Uint): boolean {
|
120
180
|
return this.uint.equals(i.uint);
|
121
181
|
}
|
@@ -156,7 +216,15 @@ export class Uint {
|
|
156
216
|
return new Uint(this.uint.mod(i.uint));
|
157
217
|
}
|
158
218
|
|
219
|
+
public pow(i: Uint): Uint {
|
220
|
+
return new Uint(this.uint.pow(i.toBigNumber()));
|
221
|
+
}
|
222
|
+
|
159
223
|
public toDec(): Dec {
|
160
224
|
return new Dec(new Int(this.toString()));
|
161
225
|
}
|
226
|
+
|
227
|
+
public toBigNumber(): bigInteger.BigInteger {
|
228
|
+
return this.uint;
|
229
|
+
}
|
162
230
|
}
|