UNPKG

2.48 kBJavaScriptView Raw
1'use strict';
2
3var maxArgumentCount = require('../../utils/function').maxArgumentCount;
4
5var map = require('../../utils/array').map;
6/**
7 * Attach a transform function to math.map
8 * Adds a property transform containing the transform function.
9 *
10 * This transform creates a one-based index instead of a zero-based index
11 */
12
13
14function factory(type, config, load, typed) {
15 var compileInlineExpression = load(require('./utils/compileInlineExpression'));
16 var matrix = load(require('../../type/matrix/function/matrix'));
17
18 function mapTransform(args, math, scope) {
19 var x, callback;
20
21 if (args[0]) {
22 x = args[0].compile().eval(scope);
23 }
24
25 if (args[1]) {
26 if (type.isSymbolNode(args[1]) || type.isFunctionAssignmentNode(args[1])) {
27 // a function pointer, like filter([3, -2, 5], myTestFunction)
28 callback = args[1].compile().eval(scope);
29 } else {
30 // an expression like filter([3, -2, 5], x > 0)
31 callback = compileInlineExpression(args[1], math, scope);
32 }
33 }
34
35 return map(x, callback);
36 }
37
38 mapTransform.rawArgs = true; // one-based version of map function
39
40 var map = typed('map', {
41 'Array, function': function ArrayFunction(x, callback) {
42 return _map(x, callback, x);
43 },
44 'Matrix, function': function MatrixFunction(x, callback) {
45 return matrix(_map(x.valueOf(), callback, x));
46 }
47 });
48 return mapTransform;
49}
50/**
51 * Map for a multi dimensional array. One-based indexes
52 * @param {Array} array
53 * @param {function} callback
54 * @param {Array} orig
55 * @return {Array}
56 * @private
57 */
58
59
60function _map(array, callback, orig) {
61 // figure out what number of arguments the callback function expects
62 var argsCount = maxArgumentCount(callback);
63
64 function recurse(value, index) {
65 if (Array.isArray(value)) {
66 return map(value, function (child, i) {
67 // we create a copy of the index array and append the new index value
68 return recurse(child, index.concat(i + 1)); // one based index, hence i + 1
69 });
70 } else {
71 // invoke the (typed) callback function with the right number of arguments
72 if (argsCount === 1) {
73 return callback(value);
74 } else if (argsCount === 2) {
75 return callback(value, index);
76 } else {
77 // 3 or -1
78 return callback(value, index, orig);
79 }
80 }
81 }
82
83 return recurse(array, []);
84}
85
86exports.name = 'map';
87exports.path = 'expression.transform';
88exports.factory = factory;
\No newline at end of file