pow.js (5880B)
1 "use strict"; 2 3 Object.defineProperty(exports, "__esModule", { 4 value: true 5 }); 6 exports.createPow = void 0; 7 8 var _factory = require("../../utils/factory.js"); 9 10 var _number = require("../../utils/number.js"); 11 12 var _array = require("../../utils/array.js"); 13 14 var _index = require("../../plain/number/index.js"); 15 16 var name = 'pow'; 17 var dependencies = ['typed', 'config', 'identity', 'multiply', 'matrix', 'fraction', 'number', 'Complex']; 18 var createPow = /* #__PURE__ */(0, _factory.factory)(name, dependencies, function (_ref) { 19 var typed = _ref.typed, 20 config = _ref.config, 21 identity = _ref.identity, 22 multiply = _ref.multiply, 23 matrix = _ref.matrix, 24 number = _ref.number, 25 fraction = _ref.fraction, 26 Complex = _ref.Complex; 27 28 /** 29 * Calculates the power of x to y, `x ^ y`. 30 * Matrix exponentiation is supported for square matrices `x`, and positive 31 * integer exponents `y`. 32 * 33 * For cubic roots of negative numbers, the function returns the principal 34 * root by default. In order to let the function return the real root, 35 * math.js can be configured with `math.config({predictable: true})`. 36 * To retrieve all cubic roots of a value, use `math.cbrt(x, true)`. 37 * 38 * Syntax: 39 * 40 * math.pow(x, y) 41 * 42 * Examples: 43 * 44 * math.pow(2, 3) // returns number 8 45 * 46 * const a = math.complex(2, 3) 47 * math.pow(a, 2) // returns Complex -5 + 12i 48 * 49 * const b = [[1, 2], [4, 3]] 50 * math.pow(b, 2) // returns Array [[9, 8], [16, 17]] 51 * 52 * See also: 53 * 54 * multiply, sqrt, cbrt, nthRoot 55 * 56 * @param {number | BigNumber | Complex | Unit | Array | Matrix} x The base 57 * @param {number | BigNumber | Complex} y The exponent 58 * @return {number | BigNumber | Complex | Array | Matrix} The value of `x` to the power `y` 59 */ 60 return typed(name, { 61 'number, number': _pow, 62 'Complex, Complex': function ComplexComplex(x, y) { 63 return x.pow(y); 64 }, 65 'BigNumber, BigNumber': function BigNumberBigNumber(x, y) { 66 if (y.isInteger() || x >= 0 || config.predictable) { 67 return x.pow(y); 68 } else { 69 return new Complex(x.toNumber(), 0).pow(y.toNumber(), 0); 70 } 71 }, 72 'Fraction, Fraction': function FractionFraction(x, y) { 73 var result = x.pow(y); 74 75 if (result != null) { 76 return result; 77 } 78 79 if (config.predictable) { 80 throw new Error('Result of pow is non-rational and cannot be expressed as a fraction'); 81 } else { 82 return _pow(x.valueOf(), y.valueOf()); 83 } 84 }, 85 'Array, number': _powArray, 86 'Array, BigNumber': function ArrayBigNumber(x, y) { 87 return _powArray(x, y.toNumber()); 88 }, 89 'Matrix, number': _powMatrix, 90 'Matrix, BigNumber': function MatrixBigNumber(x, y) { 91 return _powMatrix(x, y.toNumber()); 92 }, 93 'Unit, number | BigNumber': function UnitNumberBigNumber(x, y) { 94 return x.pow(y); 95 } 96 }); 97 /** 98 * Calculates the power of x to y, x^y, for two numbers. 99 * @param {number} x 100 * @param {number} y 101 * @return {number | Complex} res 102 * @private 103 */ 104 105 function _pow(x, y) { 106 // Alternatively could define a 'realmode' config option or something, but 107 // 'predictable' will work for now 108 if (config.predictable && !(0, _number.isInteger)(y) && x < 0) { 109 // Check to see if y can be represented as a fraction 110 try { 111 var yFrac = fraction(y); 112 var yNum = number(yFrac); 113 114 if (y === yNum || Math.abs((y - yNum) / y) < 1e-14) { 115 if (yFrac.d % 2 === 1) { 116 return (yFrac.n % 2 === 0 ? 1 : -1) * Math.pow(-x, y); 117 } 118 } 119 } catch (ex) {// fraction() throws an error if y is Infinity, etc. 120 } // Unable to express y as a fraction, so continue on 121 122 } // **for predictable mode** x^Infinity === NaN if x < -1 123 // N.B. this behavour is different from `Math.pow` which gives 124 // (-2)^Infinity === Infinity 125 126 127 if (config.predictable && (x < -1 && y === Infinity || x > -1 && x < 0 && y === -Infinity)) { 128 return NaN; 129 } 130 131 if ((0, _number.isInteger)(y) || x >= 0 || config.predictable) { 132 return (0, _index.powNumber)(x, y); 133 } else { 134 // TODO: the following infinity checks are duplicated from powNumber. Deduplicate this somehow 135 // x^Infinity === 0 if -1 < x < 1 136 // A real number 0 is returned instead of complex(0) 137 if (x * x < 1 && y === Infinity || x * x > 1 && y === -Infinity) { 138 return 0; 139 } 140 141 return new Complex(x, 0).pow(y, 0); 142 } 143 } 144 /** 145 * Calculate the power of a 2d array 146 * @param {Array} x must be a 2 dimensional, square matrix 147 * @param {number} y a positive, integer value 148 * @returns {Array} 149 * @private 150 */ 151 152 153 function _powArray(x, y) { 154 if (!(0, _number.isInteger)(y) || y < 0) { 155 throw new TypeError('For A^b, b must be a positive integer (value is ' + y + ')'); 156 } // verify that A is a 2 dimensional square matrix 157 158 159 var s = (0, _array.arraySize)(x); 160 161 if (s.length !== 2) { 162 throw new Error('For A^b, A must be 2 dimensional (A has ' + s.length + ' dimensions)'); 163 } 164 165 if (s[0] !== s[1]) { 166 throw new Error('For A^b, A must be square (size is ' + s[0] + 'x' + s[1] + ')'); 167 } 168 169 var res = identity(s[0]).valueOf(); 170 var px = x; 171 172 while (y >= 1) { 173 if ((y & 1) === 1) { 174 res = multiply(px, res); 175 } 176 177 y >>= 1; 178 px = multiply(px, px); 179 } 180 181 return res; 182 } 183 /** 184 * Calculate the power of a 2d matrix 185 * @param {Matrix} x must be a 2 dimensional, square matrix 186 * @param {number} y a positive, integer value 187 * @returns {Matrix} 188 * @private 189 */ 190 191 192 function _powMatrix(x, y) { 193 return matrix(_powArray(x.valueOf(), y)); 194 } 195 }); 196 exports.createPow = createPow;