Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- class BigNumber {
- constructor(num) {
- this.stepN = 8;
- this.step = ~~ Math.pow(10, this.stepN);
- if (num instanceof BigNumber) {
- this.digits = num.digits.slice();
- this.trailing0 = num.trailing0;
- } else if (typeof num === 'object') {
- this.digits = num.digits || [];
- this.trailing0 = num.trailing0 || 0;
- } else {
- this.digits = [];
- this.trailing0 = 0;
- while (num) {
- this.digits.push(num % this.step);
- num = ~~ (num / this.step);
- }
- }
- }
- multiply(other) {
- if (!(other instanceof BigNumber)) {
- return this.multiplySimple(other);
- }
- let x = 0;
- const digits = [];
- const selfLength = this.digits.length;
- const otherLength = other.digits.length;
- const totalLength = selfLength + otherLength - 1;
- for (let i = 0; i < totalLength; i ++) {
- for (let j = Math.max(0, i - otherLength + 1); j < selfLength && j <= i; j ++) {
- x += this.digits[j] * other.digits[i - j];
- }
- digits.push(x % this.step);
- x = ~~ (x / this.step);
- }
- while (x) {
- digits.push(x % this.step);
- x = ~~ (x / this.step);
- }
- let trailing0 = this.trailing0 + other.trailing0;
- while (digits.length && !digits[0]) {
- digits.shift();
- trailing0 ++;
- }
- return new BigNumber({digits, trailing0});
- }
- multiplySimple(num) {
- let x = 0;
- const digits = [];
- const length = this.digits.length;
- for (let i = 0; i < length; i ++) {
- x += this.digits[i] * num;
- digits.push(x % this.step);
- x = ~~ (x / this.step);
- }
- while (x) {
- digits.push(x % this.step);
- x = ~~ (x / this.step);
- }
- let trailing0 = this.trailing0;
- while (digits.length && !digits[0]) {
- digits.shift();
- trailing0 ++;
- }
- return new BigNumber({digits, trailing0});
- }
- pow(n) {
- const midValues = {1: new BigNumber(this)};
- const keys = [1];
- for (let i = 2; i <= n; i *= 2) {
- keys.push(i);
- const midValue = new BigNumber(midValues[i >> 1]);
- midValues[i] = midValue.multiply(midValue);
- }
- let res = new BigNumber(1);
- while (n) {
- const key = +keys.pop();
- if (key <= n) {
- n -= key;
- res = res.multiply(midValues[key]);
- }
- }
- return res;
- }
- leftpad(s, n, c='0') {
- s = s.toString();
- return s.length < n ? c.repeat(n - s.length) + s : s;
- }
- toString() {
- const res = [];
- const length = this.digits.length;
- if (length) {
- res.push(this.digits[length - 1]);
- for (let i = length - 1; i --; ) {
- res.push(this.leftpad(this.digits[i], this.stepN));
- }
- res.push('0'.repeat(this.trailing0 * this.stepN));
- } else {
- res.push(0);
- }
- return res.join('');
- }
- }
- function test1() {
- let n = new BigNumber(65);
- console.time('calculate');
- for (let i = 0; i < 65537; i ++) n = n.multiply(65);
- console.timeEnd('calculate');
- console.time('repr');
- const s = n.toString();
- console.timeEnd('repr');
- // console.log(s);
- }
- function test2() {
- let n = new BigNumber(1);
- console.time('calculate');
- for (let i = 2; i <= 2000; i ++) n = n.multiply(i);
- console.timeEnd('calculate');
- console.time('repr');
- const s = n.toString();
- console.timeEnd('repr');
- // console.log(s);
- }
- function test3() {
- const n = new BigNumber(65);
- console.time('calculate');
- const p = n.pow(65537);
- console.timeEnd('calculate');
- console.time('repr');
- const s = p.toString();
- console.timeEnd('repr');
- // console.log(s);
- }
- test1();
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement