mathjs 14.0.0 → 14.1.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.
Files changed (55) hide show
  1. package/HISTORY.md +15 -0
  2. package/NOTICE +1 -1
  3. package/README.md +7 -7
  4. package/bin/cli.js +1 -1
  5. package/lib/browser/math.js +1 -1
  6. package/lib/browser/math.js.LICENSE.txt +5 -5
  7. package/lib/browser/math.js.map +1 -1
  8. package/lib/cjs/entry/dependenciesAny/dependenciesLarger.generated.js +2 -0
  9. package/lib/cjs/entry/dependenciesAny/dependenciesRandomInt.generated.js +2 -0
  10. package/lib/cjs/entry/dependenciesAny/dependenciesSmaller.generated.js +2 -0
  11. package/lib/cjs/entry/dependenciesNumber/dependenciesRandomInt.generated.js +2 -0
  12. package/lib/cjs/entry/impureFunctionsNumber.generated.js +1 -1
  13. package/lib/cjs/entry/pureFunctionsAny.generated.js +3 -0
  14. package/lib/cjs/entry/pureFunctionsNumber.generated.js +5 -4
  15. package/lib/cjs/expression/embeddedDocs/function/arithmetic/sign.js +1 -1
  16. package/lib/cjs/function/algebra/derivative.js +64 -77
  17. package/lib/cjs/function/arithmetic/log.js +12 -5
  18. package/lib/cjs/function/arithmetic/log10.js +15 -7
  19. package/lib/cjs/function/arithmetic/log2.js +9 -4
  20. package/lib/cjs/function/probability/randomInt.js +26 -3
  21. package/lib/cjs/function/relational/larger.js +12 -4
  22. package/lib/cjs/function/relational/smaller.js +12 -4
  23. package/lib/cjs/function/statistics/max.js +1 -1
  24. package/lib/cjs/function/statistics/min.js +1 -1
  25. package/lib/cjs/function/string/print.js +2 -2
  26. package/lib/cjs/function/utils/isInteger.js +1 -1
  27. package/lib/cjs/header.js +3 -3
  28. package/lib/cjs/utils/bigint.js +33 -0
  29. package/lib/cjs/utils/number.js +7 -19
  30. package/lib/cjs/version.js +1 -1
  31. package/lib/esm/entry/dependenciesAny/dependenciesLarger.generated.js +2 -0
  32. package/lib/esm/entry/dependenciesAny/dependenciesRandomInt.generated.js +2 -0
  33. package/lib/esm/entry/dependenciesAny/dependenciesSmaller.generated.js +2 -0
  34. package/lib/esm/entry/dependenciesNumber/dependenciesRandomInt.generated.js +2 -0
  35. package/lib/esm/entry/impureFunctionsNumber.generated.js +2 -2
  36. package/lib/esm/entry/pureFunctionsAny.generated.js +3 -0
  37. package/lib/esm/entry/pureFunctionsNumber.generated.js +6 -5
  38. package/lib/esm/expression/embeddedDocs/function/arithmetic/sign.js +1 -1
  39. package/lib/esm/function/algebra/derivative.js +64 -77
  40. package/lib/esm/function/arithmetic/log.js +12 -5
  41. package/lib/esm/function/arithmetic/log10.js +16 -8
  42. package/lib/esm/function/arithmetic/log2.js +9 -4
  43. package/lib/esm/function/probability/randomInt.js +26 -3
  44. package/lib/esm/function/relational/larger.js +12 -4
  45. package/lib/esm/function/relational/smaller.js +12 -4
  46. package/lib/esm/function/statistics/max.js +1 -1
  47. package/lib/esm/function/statistics/min.js +1 -1
  48. package/lib/esm/function/string/print.js +2 -2
  49. package/lib/esm/function/utils/isInteger.js +1 -1
  50. package/lib/esm/header.js +1 -1
  51. package/lib/esm/utils/bigint.js +27 -0
  52. package/lib/esm/utils/number.js +6 -17
  53. package/lib/esm/version.js +1 -1
  54. package/package.json +19 -17
  55. package/types/index.d.ts +5 -8
@@ -60,9 +60,18 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
60
60
  var options = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {
61
61
  simplify: true
62
62
  };
63
- var constNodes = {};
64
- constTag(constNodes, expr, variable.name);
65
- var res = _derivative(expr, constNodes);
63
+ var cache = new Map();
64
+ var variableName = variable.name;
65
+ function isConstCached(node) {
66
+ var cached = cache.get(node);
67
+ if (cached !== undefined) {
68
+ return cached;
69
+ }
70
+ var res = _isConst(isConstCached, node, variableName);
71
+ cache.set(node, res);
72
+ return res;
73
+ }
74
+ var res = _derivative(expr, isConstCached);
66
75
  return options.simplify ? simplify(res) : res;
67
76
  }
68
77
  function parseIdentifier(string) {
@@ -82,9 +91,8 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
82
91
  'Node, SymbolNode, ConstantNode': function (expr, variable, {order}) {
83
92
  let res = expr
84
93
  for (let i = 0; i < order; i++) {
85
- let constNodes = {}
86
- constTag(constNodes, expr, variable.name)
87
- res = _derivative(res, constNodes)
94
+ <create caching isConst>
95
+ res = _derivative(res, isConst)
88
96
  }
89
97
  return res
90
98
  }
@@ -127,56 +135,39 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
127
135
  });
128
136
 
129
137
  /**
130
- * Does a depth-first search on the expression tree to identify what Nodes
131
- * are constants (e.g. 2 + 2), and stores the ones that are constants in
132
- * constNodes. Classification is done as follows:
138
+ * Checks if a node is constants (e.g. 2 + 2).
139
+ * Accepts (usually memoized) version of self as the first parameter for recursive calls.
140
+ * Classification is done as follows:
133
141
  *
134
142
  * 1. ConstantNodes are constants.
135
143
  * 2. If there exists a SymbolNode, of which we are differentiating over,
136
144
  * in the subtree it is not constant.
137
145
  *
138
- * @param {Object} constNodes Holds the nodes that are constant
146
+ * @param {function} isConst Function that tells whether sub-expression is a constant
139
147
  * @param {ConstantNode | SymbolNode | ParenthesisNode | FunctionNode | OperatorNode} node
140
148
  * @param {string} varName Variable that we are differentiating
141
149
  * @return {boolean} if node is constant
142
150
  */
143
- // TODO: can we rewrite constTag into a pure function?
144
- var constTag = typed('constTag', {
145
- 'Object, ConstantNode, string': function Object_ConstantNode_string(constNodes, node) {
146
- constNodes[node] = true;
151
+ var _isConst = typed('_isConst', {
152
+ 'function, ConstantNode, string': function function_ConstantNode_string() {
147
153
  return true;
148
154
  },
149
- 'Object, SymbolNode, string': function Object_SymbolNode_string(constNodes, node, varName) {
155
+ 'function, SymbolNode, string': function function_SymbolNode_string(isConst, node, varName) {
150
156
  // Treat other variables like constants. For reasoning, see:
151
157
  // https://en.wikipedia.org/wiki/Partial_derivative
152
- if (node.name !== varName) {
153
- constNodes[node] = true;
154
- return true;
155
- }
156
- return false;
158
+ return node.name !== varName;
157
159
  },
158
- 'Object, ParenthesisNode, string': function Object_ParenthesisNode_string(constNodes, node, varName) {
159
- return constTag(constNodes, node.content, varName);
160
+ 'function, ParenthesisNode, string': function function_ParenthesisNode_string(isConst, node, varName) {
161
+ return isConst(node.content, varName);
160
162
  },
161
- 'Object, FunctionAssignmentNode, string': function Object_FunctionAssignmentNode_string(constNodes, node, varName) {
163
+ 'function, FunctionAssignmentNode, string': function function_FunctionAssignmentNode_string(isConst, node, varName) {
162
164
  if (!node.params.includes(varName)) {
163
- constNodes[node] = true;
164
165
  return true;
165
166
  }
166
- return constTag(constNodes, node.expr, varName);
167
+ return isConst(node.expr, varName);
167
168
  },
168
- 'Object, FunctionNode | OperatorNode, string': function Object_FunctionNode__OperatorNode_string(constNodes, node, varName) {
169
- if (node.args.length > 0) {
170
- var isConst = constTag(constNodes, node.args[0], varName);
171
- for (var i = 1; i < node.args.length; ++i) {
172
- isConst = constTag(constNodes, node.args[i], varName) && isConst;
173
- }
174
- if (isConst) {
175
- constNodes[node] = true;
176
- return true;
177
- }
178
- }
179
- return false;
169
+ 'function, FunctionNode | OperatorNode, string': function function_FunctionNode__OperatorNode_string(isConst, node, varName) {
170
+ return node.args.every(arg => isConst(arg, varName));
180
171
  }
181
172
  });
182
173
 
@@ -184,30 +175,30 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
184
175
  * Applies differentiation rules.
185
176
  *
186
177
  * @param {ConstantNode | SymbolNode | ParenthesisNode | FunctionNode | OperatorNode} node
187
- * @param {Object} constNodes Holds the nodes that are constant
178
+ * @param {function} isConst Function that tells if a node is constant
188
179
  * @return {ConstantNode | SymbolNode | ParenthesisNode | FunctionNode | OperatorNode} The derivative of `expr`
189
180
  */
190
181
  var _derivative = typed('_derivative', {
191
- 'ConstantNode, Object': function ConstantNode_Object(node) {
182
+ 'ConstantNode, function': function ConstantNode_function() {
192
183
  return createConstantNode(0);
193
184
  },
194
- 'SymbolNode, Object': function SymbolNode_Object(node, constNodes) {
195
- if (constNodes[node] !== undefined) {
185
+ 'SymbolNode, function': function SymbolNode_function(node, isConst) {
186
+ if (isConst(node)) {
196
187
  return createConstantNode(0);
197
188
  }
198
189
  return createConstantNode(1);
199
190
  },
200
- 'ParenthesisNode, Object': function ParenthesisNode_Object(node, constNodes) {
201
- return new ParenthesisNode(_derivative(node.content, constNodes));
191
+ 'ParenthesisNode, function': function ParenthesisNode_function(node, isConst) {
192
+ return new ParenthesisNode(_derivative(node.content, isConst));
202
193
  },
203
- 'FunctionAssignmentNode, Object': function FunctionAssignmentNode_Object(node, constNodes) {
204
- if (constNodes[node] !== undefined) {
194
+ 'FunctionAssignmentNode, function': function FunctionAssignmentNode_function(node, isConst) {
195
+ if (isConst(node)) {
205
196
  return createConstantNode(0);
206
197
  }
207
- return _derivative(node.expr, constNodes);
198
+ return _derivative(node.expr, isConst);
208
199
  },
209
- 'FunctionNode, Object': function FunctionNode_Object(node, constNodes) {
210
- if (constNodes[node] !== undefined) {
200
+ 'FunctionNode, function': function FunctionNode_function(node, isConst) {
201
+ if (isConst(node)) {
211
202
  return createConstantNode(0);
212
203
  }
213
204
  var arg0 = node.args[0];
@@ -231,10 +222,7 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
231
222
  } else if (node.args.length === 2) {
232
223
  // Rearrange from nthRoot(x, a) -> x^(1/a)
233
224
  arg1 = new OperatorNode('/', 'divide', [createConstantNode(1), node.args[1]]);
234
-
235
- // Is a variable?
236
- constNodes[arg1] = constNodes[node.args[1]];
237
- return _derivative(new OperatorNode('^', 'pow', [arg0, arg1]), constNodes);
225
+ return _derivative(new OperatorNode('^', 'pow', [arg0, arg1]), isConst);
238
226
  }
239
227
  break;
240
228
  case 'log10':
@@ -245,20 +233,19 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
245
233
  // d/dx(log(x)) = 1 / x
246
234
  funcDerivative = arg0.clone();
247
235
  div = true;
248
- } else if (node.args.length === 1 && arg1 || node.args.length === 2 && constNodes[node.args[1]] !== undefined) {
236
+ } else if (node.args.length === 1 && arg1 || node.args.length === 2 && isConst(node.args[1])) {
249
237
  // d/dx(log(x, c)) = 1 / (x*ln(c))
250
238
  funcDerivative = new OperatorNode('*', 'multiply', [arg0.clone(), new FunctionNode('log', [arg1 || node.args[1]])]);
251
239
  div = true;
252
240
  } else if (node.args.length === 2) {
253
241
  // d/dx(log(f(x), g(x))) = d/dx(log(f(x)) / log(g(x)))
254
- return _derivative(new OperatorNode('/', 'divide', [new FunctionNode('log', [arg0]), new FunctionNode('log', [node.args[1]])]), constNodes);
242
+ return _derivative(new OperatorNode('/', 'divide', [new FunctionNode('log', [arg0]), new FunctionNode('log', [node.args[1]])]), isConst);
255
243
  }
256
244
  break;
257
245
  case 'pow':
258
246
  if (node.args.length === 2) {
259
- constNodes[arg1] = constNodes[node.args[1]];
260
247
  // Pass to pow operator node parser
261
- return _derivative(new OperatorNode('^', 'pow', [arg0, node.args[1]]), constNodes);
248
+ return _derivative(new OperatorNode('^', 'pow', [arg0, node.args[1]]), isConst);
262
249
  }
263
250
  break;
264
251
  case 'exp':
@@ -404,51 +391,51 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
404
391
  /* Apply chain rule to all functions:
405
392
  F(x) = f(g(x))
406
393
  F'(x) = g'(x)*f'(g(x)) */
407
- var chainDerivative = _derivative(arg0, constNodes);
394
+ var chainDerivative = _derivative(arg0, isConst);
408
395
  if (negative) {
409
396
  chainDerivative = new OperatorNode('-', 'unaryMinus', [chainDerivative]);
410
397
  }
411
398
  return new OperatorNode(op, func, [chainDerivative, funcDerivative]);
412
399
  },
413
- 'OperatorNode, Object': function OperatorNode_Object(node, constNodes) {
414
- if (constNodes[node] !== undefined) {
400
+ 'OperatorNode, function': function OperatorNode_function(node, isConst) {
401
+ if (isConst(node)) {
415
402
  return createConstantNode(0);
416
403
  }
417
404
  if (node.op === '+') {
418
405
  // d/dx(sum(f(x)) = sum(f'(x))
419
406
  return new OperatorNode(node.op, node.fn, node.args.map(function (arg) {
420
- return _derivative(arg, constNodes);
407
+ return _derivative(arg, isConst);
421
408
  }));
422
409
  }
423
410
  if (node.op === '-') {
424
411
  // d/dx(+/-f(x)) = +/-f'(x)
425
412
  if (node.isUnary()) {
426
- return new OperatorNode(node.op, node.fn, [_derivative(node.args[0], constNodes)]);
413
+ return new OperatorNode(node.op, node.fn, [_derivative(node.args[0], isConst)]);
427
414
  }
428
415
 
429
416
  // Linearity of differentiation, d/dx(f(x) +/- g(x)) = f'(x) +/- g'(x)
430
417
  if (node.isBinary()) {
431
- return new OperatorNode(node.op, node.fn, [_derivative(node.args[0], constNodes), _derivative(node.args[1], constNodes)]);
418
+ return new OperatorNode(node.op, node.fn, [_derivative(node.args[0], isConst), _derivative(node.args[1], isConst)]);
432
419
  }
433
420
  }
434
421
  if (node.op === '*') {
435
422
  // d/dx(c*f(x)) = c*f'(x)
436
423
  var constantTerms = node.args.filter(function (arg) {
437
- return constNodes[arg] !== undefined;
424
+ return isConst(arg);
438
425
  });
439
426
  if (constantTerms.length > 0) {
440
427
  var nonConstantTerms = node.args.filter(function (arg) {
441
- return constNodes[arg] === undefined;
428
+ return !isConst(arg);
442
429
  });
443
430
  var nonConstantNode = nonConstantTerms.length === 1 ? nonConstantTerms[0] : new OperatorNode('*', 'multiply', nonConstantTerms);
444
- var newArgs = constantTerms.concat(_derivative(nonConstantNode, constNodes));
431
+ var newArgs = constantTerms.concat(_derivative(nonConstantNode, isConst));
445
432
  return new OperatorNode('*', 'multiply', newArgs);
446
433
  }
447
434
 
448
435
  // Product Rule, d/dx(f(x)*g(x)) = f'(x)*g(x) + f(x)*g'(x)
449
436
  return new OperatorNode('+', 'add', node.args.map(function (argOuter) {
450
437
  return new OperatorNode('*', 'multiply', node.args.map(function (argInner) {
451
- return argInner === argOuter ? _derivative(argInner, constNodes) : argInner.clone();
438
+ return argInner === argOuter ? _derivative(argInner, isConst) : argInner.clone();
452
439
  }));
453
440
  }));
454
441
  }
@@ -457,31 +444,31 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
457
444
  var arg1 = node.args[1];
458
445
 
459
446
  // d/dx(f(x) / c) = f'(x) / c
460
- if (constNodes[arg1] !== undefined) {
461
- return new OperatorNode('/', 'divide', [_derivative(arg0, constNodes), arg1]);
447
+ if (isConst(arg1)) {
448
+ return new OperatorNode('/', 'divide', [_derivative(arg0, isConst), arg1]);
462
449
  }
463
450
 
464
451
  // Reciprocal Rule, d/dx(c / f(x)) = -c(f'(x)/f(x)^2)
465
- if (constNodes[arg0] !== undefined) {
466
- return new OperatorNode('*', 'multiply', [new OperatorNode('-', 'unaryMinus', [arg0]), new OperatorNode('/', 'divide', [_derivative(arg1, constNodes), new OperatorNode('^', 'pow', [arg1.clone(), createConstantNode(2)])])]);
452
+ if (isConst(arg0)) {
453
+ return new OperatorNode('*', 'multiply', [new OperatorNode('-', 'unaryMinus', [arg0]), new OperatorNode('/', 'divide', [_derivative(arg1, isConst), new OperatorNode('^', 'pow', [arg1.clone(), createConstantNode(2)])])]);
467
454
  }
468
455
 
469
456
  // Quotient rule, d/dx(f(x) / g(x)) = (f'(x)g(x) - f(x)g'(x)) / g(x)^2
470
- return new OperatorNode('/', 'divide', [new OperatorNode('-', 'subtract', [new OperatorNode('*', 'multiply', [_derivative(arg0, constNodes), arg1.clone()]), new OperatorNode('*', 'multiply', [arg0.clone(), _derivative(arg1, constNodes)])]), new OperatorNode('^', 'pow', [arg1.clone(), createConstantNode(2)])]);
457
+ return new OperatorNode('/', 'divide', [new OperatorNode('-', 'subtract', [new OperatorNode('*', 'multiply', [_derivative(arg0, isConst), arg1.clone()]), new OperatorNode('*', 'multiply', [arg0.clone(), _derivative(arg1, isConst)])]), new OperatorNode('^', 'pow', [arg1.clone(), createConstantNode(2)])]);
471
458
  }
472
459
  if (node.op === '^' && node.isBinary()) {
473
460
  var _arg = node.args[0];
474
461
  var _arg2 = node.args[1];
475
- if (constNodes[_arg] !== undefined) {
462
+ if (isConst(_arg)) {
476
463
  // If is secretly constant; 0^f(x) = 1 (in JS), 1^f(x) = 1
477
464
  if (isConstantNode(_arg) && (isZero(_arg.value) || equal(_arg.value, 1))) {
478
465
  return createConstantNode(0);
479
466
  }
480
467
 
481
468
  // d/dx(c^f(x)) = c^f(x)*ln(c)*f'(x)
482
- return new OperatorNode('*', 'multiply', [node, new OperatorNode('*', 'multiply', [new FunctionNode('log', [_arg.clone()]), _derivative(_arg2.clone(), constNodes)])]);
469
+ return new OperatorNode('*', 'multiply', [node, new OperatorNode('*', 'multiply', [new FunctionNode('log', [_arg.clone()]), _derivative(_arg2.clone(), isConst)])]);
483
470
  }
484
- if (constNodes[_arg2] !== undefined) {
471
+ if (isConst(_arg2)) {
485
472
  if (isConstantNode(_arg2)) {
486
473
  // If is secretly constant; f(x)^0 = 1 -> d/dx(1) = 0
487
474
  if (isZero(_arg2.value)) {
@@ -489,17 +476,17 @@ export var createDerivative = /* #__PURE__ */factory(name, dependencies, _ref =>
489
476
  }
490
477
  // Ignore exponent; f(x)^1 = f(x)
491
478
  if (equal(_arg2.value, 1)) {
492
- return _derivative(_arg, constNodes);
479
+ return _derivative(_arg, isConst);
493
480
  }
494
481
  }
495
482
 
496
483
  // Elementary Power Rule, d/dx(f(x)^c) = c*f'(x)*f(x)^(c-1)
497
484
  var powMinusOne = new OperatorNode('^', 'pow', [_arg.clone(), new OperatorNode('-', 'subtract', [_arg2, createConstantNode(1)])]);
498
- return new OperatorNode('*', 'multiply', [_arg2.clone(), new OperatorNode('*', 'multiply', [_derivative(_arg, constNodes), powMinusOne])]);
485
+ return new OperatorNode('*', 'multiply', [_arg2.clone(), new OperatorNode('*', 'multiply', [_derivative(_arg, isConst), powMinusOne])]);
499
486
  }
500
487
 
501
488
  // Functional Power Rule, d/dx(f^g) = f^g*[f'*(g/f) + g'ln(f)]
502
- return new OperatorNode('*', 'multiply', [new OperatorNode('^', 'pow', [_arg.clone(), _arg2.clone()]), new OperatorNode('+', 'add', [new OperatorNode('*', 'multiply', [_derivative(_arg, constNodes), new OperatorNode('/', 'divide', [_arg2.clone(), _arg.clone()])]), new OperatorNode('*', 'multiply', [_derivative(_arg2, constNodes), new FunctionNode('log', [_arg.clone()])])])]);
489
+ return new OperatorNode('*', 'multiply', [new OperatorNode('^', 'pow', [_arg.clone(), _arg2.clone()]), new OperatorNode('+', 'add', [new OperatorNode('*', 'multiply', [_derivative(_arg, isConst), new OperatorNode('/', 'divide', [_arg2.clone(), _arg.clone()])]), new OperatorNode('*', 'multiply', [_derivative(_arg2, isConst), new FunctionNode('log', [_arg.clone()])])])]);
503
490
  }
504
491
  throw new Error('Cannot process operator "' + node.op + '" in derivative: ' + 'the operator is not supported, undefined, or the number of arguments passed to it are not supported');
505
492
  }
@@ -1,7 +1,9 @@
1
1
  import { factory } from '../../utils/factory.js';
2
+ import { promoteLogarithm } from '../../utils/bigint.js';
2
3
  import { logNumber } from '../../plain/number/index.js';
3
4
  var name = 'log';
4
5
  var dependencies = ['config', 'typed', 'typeOf', 'divideScalar', 'Complex'];
6
+ var nlg16 = Math.log(16);
5
7
  export var createLog = /* #__PURE__ */factory(name, dependencies, _ref => {
6
8
  var {
7
9
  typed,
@@ -45,24 +47,29 @@ export var createLog = /* #__PURE__ */factory(name, dependencies, _ref => {
45
47
  * @return {number | BigNumber | Fraction | Complex}
46
48
  * Returns the logarithm of `x`
47
49
  */
50
+ function complexLog(c) {
51
+ return c.log();
52
+ }
53
+ function complexLogNumber(x) {
54
+ return complexLog(new Complex(x, 0));
55
+ }
48
56
  return typed(name, {
49
57
  number: function number(x) {
50
58
  if (x >= 0 || config.predictable) {
51
59
  return logNumber(x);
52
60
  } else {
53
61
  // negative value -> complex value computation
54
- return new Complex(x, 0).log();
62
+ return complexLogNumber(x);
55
63
  }
56
64
  },
57
- Complex: function Complex(x) {
58
- return x.log();
59
- },
65
+ bigint: promoteLogarithm(nlg16, logNumber, config, complexLogNumber),
66
+ Complex: complexLog,
60
67
  BigNumber: function BigNumber(x) {
61
68
  if (!x.isNegative() || config.predictable) {
62
69
  return x.ln();
63
70
  } else {
64
71
  // downgrade to number, return Complex valued result
65
- return new Complex(x.toNumber(), 0).log();
72
+ return complexLogNumber(x.toNumber());
66
73
  }
67
74
  },
68
75
  'any, any': typed.referToSelf(self => (x, base) => {
@@ -1,13 +1,15 @@
1
- import { factory } from '../../utils/factory.js';
2
- import { deepMap } from '../../utils/collection.js';
3
1
  import { log10Number } from '../../plain/number/index.js';
2
+ import { promoteLogarithm } from '../../utils/bigint.js';
3
+ import { deepMap } from '../../utils/collection.js';
4
+ import { factory } from '../../utils/factory.js';
4
5
  var name = 'log10';
5
6
  var dependencies = ['typed', 'config', 'Complex'];
7
+ var log16 = log10Number(16);
6
8
  export var createLog10 = /* #__PURE__ */factory(name, dependencies, _ref => {
7
9
  var {
8
10
  typed,
9
11
  config,
10
- Complex: _Complex
12
+ Complex
11
13
  } = _ref;
12
14
  /**
13
15
  * Calculate the 10-base logarithm of a value. This is the same as calculating `log(x, 10)`.
@@ -34,24 +36,30 @@ export var createLog10 = /* #__PURE__ */factory(name, dependencies, _ref => {
34
36
  * @return {number | BigNumber | Complex | Array | Matrix}
35
37
  * Returns the 10-base logarithm of `x`
36
38
  */
39
+
40
+ function complexLog(c) {
41
+ return c.log().div(Math.LN10);
42
+ }
43
+ function complexLogNumber(x) {
44
+ return complexLog(new Complex(x, 0));
45
+ }
37
46
  return typed(name, {
38
47
  number: function number(x) {
39
48
  if (x >= 0 || config.predictable) {
40
49
  return log10Number(x);
41
50
  } else {
42
51
  // negative value -> complex value computation
43
- return new _Complex(x, 0).log().div(Math.LN10);
52
+ return complexLogNumber(x);
44
53
  }
45
54
  },
46
- Complex: function Complex(x) {
47
- return new _Complex(x).log().div(Math.LN10);
48
- },
55
+ bigint: promoteLogarithm(log16, log10Number, config, complexLogNumber),
56
+ Complex: complexLog,
49
57
  BigNumber: function BigNumber(x) {
50
58
  if (!x.isNegative() || config.predictable) {
51
59
  return x.log();
52
60
  } else {
53
61
  // downgrade to number, return Complex valued result
54
- return new _Complex(x.toNumber(), 0).log().div(Math.LN10);
62
+ return complexLogNumber(x.toNumber());
55
63
  }
56
64
  },
57
65
  'Array | Matrix': typed.referToSelf(self => x => deepMap(x, self))
@@ -1,6 +1,7 @@
1
- import { factory } from '../../utils/factory.js';
2
- import { deepMap } from '../../utils/collection.js';
3
1
  import { log2Number } from '../../plain/number/index.js';
2
+ import { promoteLogarithm } from '../../utils/bigint.js';
3
+ import { deepMap } from '../../utils/collection.js';
4
+ import { factory } from '../../utils/factory.js';
4
5
  var name = 'log2';
5
6
  var dependencies = ['typed', 'config', 'Complex'];
6
7
  export var createLog2 = /* #__PURE__ */factory(name, dependencies, _ref => {
@@ -34,22 +35,26 @@ export var createLog2 = /* #__PURE__ */factory(name, dependencies, _ref => {
34
35
  * @return {number | BigNumber | Complex | Array | Matrix}
35
36
  * Returns the 2-base logarithm of `x`
36
37
  */
38
+ function complexLog2Number(x) {
39
+ return _log2Complex(new Complex(x, 0));
40
+ }
37
41
  return typed(name, {
38
42
  number: function number(x) {
39
43
  if (x >= 0 || config.predictable) {
40
44
  return log2Number(x);
41
45
  } else {
42
46
  // negative value -> complex value computation
43
- return _log2Complex(new Complex(x, 0));
47
+ return complexLog2Number(x);
44
48
  }
45
49
  },
50
+ bigint: promoteLogarithm(4, log2Number, config, complexLog2Number),
46
51
  Complex: _log2Complex,
47
52
  BigNumber: function BigNumber(x) {
48
53
  if (!x.isNegative() || config.predictable) {
49
54
  return x.log(2);
50
55
  } else {
51
56
  // downgrade to number, return Complex valued result
52
- return _log2Complex(new Complex(x.toNumber(), 0));
57
+ return complexLog2Number(x.toNumber());
53
58
  }
54
59
  },
55
60
  'Array | Matrix': typed.referToSelf(self => x => deepMap(x, self))
@@ -3,11 +3,13 @@ import { randomMatrix } from './util/randomMatrix.js';
3
3
  import { createRng } from './util/seededRNG.js';
4
4
  import { isMatrix } from '../../utils/is.js';
5
5
  var name = 'randomInt';
6
- var dependencies = ['typed', 'config', '?on'];
6
+ var dependencies = ['typed', 'config', 'log2', '?on'];
7
+ var simpleCutoff = 2n ** 30n;
7
8
  export var createRandomInt = /* #__PURE__ */factory(name, dependencies, _ref => {
8
9
  var {
9
10
  typed,
10
11
  config,
12
+ log2,
11
13
  on
12
14
  } = _ref;
13
15
  // seeded pseudo random number generator
@@ -26,7 +28,7 @@ export var createRandomInt = /* #__PURE__ */factory(name, dependencies, _ref =>
26
28
  *
27
29
  * Syntax:
28
30
  *
29
- * math.randomInt() // generate a random integer between 0 and 1
31
+ * math.randomInt() // generate either 0 or 1, randomly
30
32
  * math.randomInt(max) // generate a random integer between 0 and max
31
33
  * math.randomInt(min, max) // generate a random integer between min and max
32
34
  * math.randomInt(size) // generate a matrix with random integer between 0 and 1
@@ -50,9 +52,11 @@ export var createRandomInt = /* #__PURE__ */factory(name, dependencies, _ref =>
50
52
  * @return {number | Array | Matrix} A random integer value
51
53
  */
52
54
  return typed(name, {
53
- '': () => _randomInt(0, 1),
55
+ '': () => _randomInt(0, 2),
54
56
  number: max => _randomInt(0, max),
55
57
  'number, number': (min, max) => _randomInt(min, max),
58
+ bigint: max => _randomBigint(0n, max),
59
+ 'bigint, bigint': _randomBigint,
56
60
  'Array | Matrix': size => _randomIntMatrix(size, 0, 1),
57
61
  'Array | Matrix, number': (size, max) => _randomIntMatrix(size, 0, max),
58
62
  'Array | Matrix, number, number': (size, min, max) => _randomIntMatrix(size, min, max)
@@ -64,4 +68,23 @@ export var createRandomInt = /* #__PURE__ */factory(name, dependencies, _ref =>
64
68
  function _randomInt(min, max) {
65
69
  return Math.floor(min + rng() * (max - min));
66
70
  }
71
+ function _randomBigint(min, max) {
72
+ var width = max - min; // number of choices
73
+ if (width <= simpleCutoff) {
74
+ // do it with number type
75
+ return min + BigInt(_randomInt(0, Number(width)));
76
+ }
77
+ // Too big to choose accurately that way. Instead, choose the correct
78
+ // number of random bits to cover the width, and repeat until the
79
+ // resulting number falls within the width
80
+ var bits = log2(width);
81
+ var picked = width;
82
+ while (picked >= width) {
83
+ picked = 0n;
84
+ for (var i = 0; i < bits; ++i) {
85
+ picked = 2n * picked + (rng() < 0.5 ? 0n : 1n);
86
+ }
87
+ }
88
+ return min + picked;
89
+ }
67
90
  });
@@ -7,11 +7,12 @@ import { createMatAlgo12xSfs } from '../../type/matrix/utils/matAlgo12xSfs.js';
7
7
  import { createMatrixAlgorithmSuite } from '../../type/matrix/utils/matrixAlgorithmSuite.js';
8
8
  import { createCompareUnits } from './compareUnits.js';
9
9
  var name = 'larger';
10
- var dependencies = ['typed', 'config', 'matrix', 'DenseMatrix', 'concat', 'SparseMatrix'];
10
+ var dependencies = ['typed', 'config', 'bignumber', 'matrix', 'DenseMatrix', 'concat', 'SparseMatrix'];
11
11
  export var createLarger = /* #__PURE__ */factory(name, dependencies, _ref => {
12
12
  var {
13
13
  typed,
14
14
  config,
15
+ bignumber,
15
16
  matrix,
16
17
  DenseMatrix,
17
18
  concat,
@@ -68,16 +69,23 @@ export var createLarger = /* #__PURE__ */factory(name, dependencies, _ref => {
68
69
  * @param {number | BigNumber | bigint | Fraction | boolean | Unit | string | Array | Matrix} y Second value to compare
69
70
  * @return {boolean | Array | Matrix} Returns true when the x is larger than y, else returns false
70
71
  */
72
+ function bignumLarger(x, y) {
73
+ return x.gt(y) && !bigNearlyEqual(x, y, config.relTol, config.absTol);
74
+ }
71
75
  return typed(name, createLargerNumber({
72
76
  typed,
73
77
  config
74
78
  }), {
75
79
  'boolean, boolean': (x, y) => x > y,
76
- 'BigNumber, BigNumber': function BigNumber_BigNumber(x, y) {
77
- return x.gt(y) && !bigNearlyEqual(x, y, config.relTol, config.absTol);
78
- },
80
+ 'BigNumber, BigNumber': bignumLarger,
79
81
  'bigint, bigint': (x, y) => x > y,
80
82
  'Fraction, Fraction': (x, y) => x.compare(y) === 1,
83
+ 'Fraction, BigNumber': function Fraction_BigNumber(x, y) {
84
+ return bignumLarger(bignumber(x), y);
85
+ },
86
+ 'BigNumber, Fraction': function BigNumber_Fraction(x, y) {
87
+ return bignumLarger(x, bignumber(y));
88
+ },
81
89
  'Complex, Complex': function Complex_Complex() {
82
90
  throw new TypeError('No ordering relation is defined for complex numbers');
83
91
  }
@@ -7,11 +7,12 @@ import { createMatAlgo12xSfs } from '../../type/matrix/utils/matAlgo12xSfs.js';
7
7
  import { createMatrixAlgorithmSuite } from '../../type/matrix/utils/matrixAlgorithmSuite.js';
8
8
  import { createCompareUnits } from './compareUnits.js';
9
9
  var name = 'smaller';
10
- var dependencies = ['typed', 'config', 'matrix', 'DenseMatrix', 'concat', 'SparseMatrix'];
10
+ var dependencies = ['typed', 'config', 'bignumber', 'matrix', 'DenseMatrix', 'concat', 'SparseMatrix'];
11
11
  export var createSmaller = /* #__PURE__ */factory(name, dependencies, _ref => {
12
12
  var {
13
13
  typed,
14
14
  config,
15
+ bignumber,
15
16
  matrix,
16
17
  DenseMatrix,
17
18
  concat,
@@ -68,16 +69,23 @@ export var createSmaller = /* #__PURE__ */factory(name, dependencies, _ref => {
68
69
  * @param {number | BigNumber | bigint | Fraction | boolean | Unit | string | Array | Matrix} y Second value to compare
69
70
  * @return {boolean | Array | Matrix} Returns true when the x is smaller than y, else returns false
70
71
  */
72
+ function bignumSmaller(x, y) {
73
+ return x.lt(y) && !bigNearlyEqual(x, y, config.relTol, config.absTol);
74
+ }
71
75
  return typed(name, createSmallerNumber({
72
76
  typed,
73
77
  config
74
78
  }), {
75
79
  'boolean, boolean': (x, y) => x < y,
76
- 'BigNumber, BigNumber': function BigNumber_BigNumber(x, y) {
77
- return x.lt(y) && !bigNearlyEqual(x, y, config.relTol, config.absTol);
78
- },
80
+ 'BigNumber, BigNumber': bignumSmaller,
79
81
  'bigint, bigint': (x, y) => x < y,
80
82
  'Fraction, Fraction': (x, y) => x.compare(y) === -1,
83
+ 'Fraction, BigNumber': function Fraction_BigNumber(x, y) {
84
+ return bignumSmaller(bignumber(x), y);
85
+ },
86
+ 'BigNumber, Fraction': function BigNumber_Fraction(x, y) {
87
+ return bignumSmaller(x, bignumber(y));
88
+ },
81
89
  'Complex, Complex': function Complex_Complex(x, y) {
82
90
  throw new TypeError('No ordering relation is defined for complex numbers');
83
91
  }
@@ -83,7 +83,7 @@ export var createMax = /* #__PURE__ */factory(name, dependencies, _ref => {
83
83
  var res;
84
84
  deepForEach(array, function (value) {
85
85
  try {
86
- if (isNaN(value) && typeof value === 'number') {
86
+ if (typeof value === 'number' && isNaN(value)) {
87
87
  res = NaN;
88
88
  } else if (res === undefined || larger(value, res)) {
89
89
  res = value;
@@ -83,7 +83,7 @@ export var createMin = /* #__PURE__ */factory(name, dependencies, _ref => {
83
83
  var min;
84
84
  deepForEach(array, function (value) {
85
85
  try {
86
- if (isNaN(value) && typeof value === 'number') {
86
+ if (typeof value === 'number' && isNaN(value)) {
87
87
  min = NaN;
88
88
  } else if (min === undefined || smaller(value, min)) {
89
89
  min = value;
@@ -25,12 +25,12 @@ export var createPrint = /* #__PURE__ */factory(name, dependencies, _ref => {
25
25
  * // the following outputs: 'The value of pi is 3.141592654'
26
26
  * math.print('The value of pi is $pi', {pi: math.pi}, 10)
27
27
  *
28
- * // the following outputs: 'hello Mary! The date is 2013-03-23'
28
+ * // the following outputs: 'Hello Mary! The date is 2013-03-23'
29
29
  * math.print('Hello $user.name! The date is $date', {
30
30
  * user: {
31
31
  * name: 'Mary',
32
32
  * },
33
- * date: new Date(2013, 2, 23).toISOString().substring(0, 10)
33
+ * date: '2013-03-23'
34
34
  * })
35
35
  *
36
36
  * // the following outputs: 'My favorite fruits are apples and bananas !'
@@ -26,7 +26,7 @@ export var createIsInteger = /* #__PURE__ */factory(name, dependencies, _ref =>
26
26
  * math.isInteger(math.fraction(4)) // returns true
27
27
  * math.isInteger('3') // returns true
28
28
  * math.isInteger([3, 0.5, -2]) // returns [true, false, true]
29
- * math.isInteger(math.complex('2-4i')) // throws an error
29
+ * math.isInteger(math.complex('2-4i')) // throws TypeError
30
30
  *
31
31
  * See also:
32
32
  *
package/lib/esm/header.js CHANGED
@@ -10,7 +10,7 @@
10
10
  * @date @@date
11
11
  *
12
12
  * @license
13
- * Copyright (C) 2013-2024 Jos de Jong <wjosdejong@gmail.com>
13
+ * Copyright (C) 2013-2025 Jos de Jong <wjosdejong@gmail.com>
14
14
  *
15
15
  * Licensed under the Apache License, Version 2.0 (the "License"); you may not
16
16
  * use this file except in compliance with the License. You may obtain a copy