diff --git a/src/expression/parse.js b/src/expression/parse.js index c300b8cf98..e01e7c85bf 100644 --- a/src/expression/parse.js +++ b/src/expression/parse.js @@ -1217,7 +1217,6 @@ export const createParse = /* #__PURE__ */ factory(name, dependencies, ({ * @private */ function parseUnary (state) { - let name, params, fn const operators = { '-': 'unaryMinus', '+': 'unaryPlus', @@ -1226,13 +1225,22 @@ export const createParse = /* #__PURE__ */ factory(name, dependencies, ({ } if (hasOwnProperty(operators, state.token)) { - fn = operators[state.token] - name = state.token + const fn = operators[state.token] + const name = state.token + const saveState = Object.assign({}, state) getTokenSkipNewline(state) - params = [parseUnary(state)] - - return new OperatorNode(name, fn, params) + if (name === 'not' && state.token === '(') { + // OK, this appears to be using `not` in the syntax of an ordinary + // function call, rather than as a unary operator, so re-parse the + // `not` as a Symbol and continue from there: + Object.assign(state, saveState) + return parseSymbol(state) + } else { + // Bona-finde "unary operator" application + const params = [parseUnary(state)] + return new OperatorNode(name, fn, params) + } } return parsePow(state) diff --git a/test/unit-tests/expression/parse.test.js b/test/unit-tests/expression/parse.test.js index 444247244f..58a078f8ef 100644 --- a/test/unit-tests/expression/parse.test.js +++ b/test/unit-tests/expression/parse.test.js @@ -2054,6 +2054,16 @@ describe('parse', function () { assert.strictEqual(parseAndEval('4 + not 2'), 4) assert.strictEqual(parseAndEval('10+not not 3'), 11) + + assert.strictEqual(parseAndEval('not(2)'), false) + // not used in function call syntax has function-call precedence + assert.deepStrictEqual( + parseAndEval('not([0, 1]).map(_(x) = equal(x, true) ? 7 : -1)'), + math.matrix([7, -1])) + // not used as operator has unary-prefix-operator precedence + assert.deepStrictEqual( + parseAndEval('not [0, 1].map(_(x) = equal(x, true) ? 7 : -1)'), + math.matrix([false, false])) }) it('should parse minus -', function () {