mathsteps-experimental-fork
Version:
Step by step math solutions. Experimental Fork
146 lines (141 loc) • 7.22 kB
JavaScript
;
Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
const config = require('../../config.js');
const ruleHelper = require('../../newServices/ruleHelper.js');
const commonRulesMistakes = require('../mistakes/commonRulesMistakes.js');
const ChangeTypes = require('../../types/changeType/ChangeTypes.js');
const cleanString = require('../../util/cleanString.js');
const index = require('../../node/index.js');
const kemuSimplifyCommonServices = require('../kemuSimplifyCommonServices.js');
const { ADD_FRACTIONS, COMMON_DENOMINATOR, DISTRIBUTE_NEGATIVE_ONE, DIVISION_BY_NEGATIVE_ONE, DIVISION_BY_ONE, KEMU_REMOVE_DOUBLE_FRACTION, MULTIPLY_BY_ZERO, MULTIPLY_FRACTIONS, PERCENTS_ADD, PERCENTS_CONVERT_TO_FRACTION, PERCENTS_SUB, REDUCE_EXPONENT_BY_ZERO, REDUCE_ZERO_NUMERATOR, REMOVE_ADDING_ZERO, REMOVE_EXPONENT_BASE_ONE, REMOVE_EXPONENT_BASE_ZERO, REMOVE_EXPONENT_BY_ONE, REMOVE_MULTIPLYING_BY_NEGATIVE_ONE, REMOVE_MULTIPLYING_BY_ONE, RESOLVE_DOUBLE_MINUS, SIMPLIFY_ARITHMETIC__ADD, SIMPLIFY_ARITHMETIC__MULTIPLY, SIMPLIFY_ARITHMETIC__POWER, SIMPLIFY_ARITHMETIC__SUBTRACT, SIMPLIFY_SIGNS } = ChangeTypes.ChangeTypes;
const makeConstant = (value) => index.default.Creator.constant(value);
const makeOp = (operator, operands) => index.default.Creator.operator(operator, operands);
const makePercent = (value) => index.default.Creator.percent(makeConstant(value));
const makeConstantFromOp = (operation) => (node, vars) => makeConstant(operation(vars.c1.value, vars.c2.value));
const _commonPoolOfRules = [
// Power
{ l: "n^0", r: "1", id: REDUCE_EXPONENT_BY_ZERO },
{ l: "n^1", r: "n", id: REMOVE_EXPONENT_BY_ONE },
{ l: "0^n", r: "0", id: REMOVE_EXPONENT_BASE_ZERO },
{ l: "1^n", r: "1", id: REMOVE_EXPONENT_BASE_ONE },
// Multiply
{ l: "0*n", r: "0", id: MULTIPLY_BY_ZERO },
{ l: "n*0", r: "0", id: MULTIPLY_BY_ZERO },
{ l: "1*n", r: "n", id: REMOVE_MULTIPLYING_BY_ONE },
{ l: "n*1", r: "n", id: REMOVE_MULTIPLYING_BY_ONE },
{ l: "-1*n", r: "-n", id: REMOVE_MULTIPLYING_BY_NEGATIVE_ONE },
// Division
{ l: "0/n", r: "0", id: REDUCE_ZERO_NUMERATOR },
{ l: "n/1", r: "n", id: DIVISION_BY_ONE },
{ l: "n/-1", r: "-n", id: DIVISION_BY_NEGATIVE_ONE },
// Addition
{ l: "n+0", r: "n", id: REMOVE_ADDING_ZERO },
{ l: "n-0", r: "n", id: REMOVE_ADDING_ZERO },
// Distribute minus one
{ l: "-(n1/n2)", r: "(-n1)/n2", id: DISTRIBUTE_NEGATIVE_ONE },
// Double minus
{ l: "-(-c)", r: "c", id: RESOLVE_DOUBLE_MINUS },
{ l: "-(-c v)", r: "c v", id: RESOLVE_DOUBLE_MINUS },
{ l: "-(-n)", r: "n", id: RESOLVE_DOUBLE_MINUS },
{ l: "n1 - (-n2)", r: "n1 + n2", id: RESOLVE_DOUBLE_MINUS },
{ l: "n1 - (-c1)", r: "n1 + c1", id: RESOLVE_DOUBLE_MINUS },
// Constant arithmetic
{
l: "c1 + c2",
id: SIMPLIFY_ARITHMETIC__ADD,
replaceFct: makeConstantFromOp(config.default.add)
},
{
l: "c1 - c2",
id: SIMPLIFY_ARITHMETIC__SUBTRACT,
replaceFct: makeConstantFromOp(config.default.subtract)
},
{
l: "c1 * c2",
id: SIMPLIFY_ARITHMETIC__MULTIPLY,
replaceFct: makeConstantFromOp(config.default.multiply)
},
{
l: "c1 ^ c2",
id: SIMPLIFY_ARITHMETIC__POWER,
replaceFct: makeConstantFromOp(config.default.pow)
},
// Percents
{ l: "percent(c1) + percent(c2)", id: PERCENTS_ADD, replaceFct: (node, vars) => makePercent(config.default.add(vars.c1.value, vars.c2.value)) },
{ l: "percent(c1) - percent(c2)", id: PERCENTS_SUB, replaceFct: (node, vars) => makePercent(config.default.subtract(vars.c1.value, vars.c2.value)) },
{ l: "percent(n)", r: "n/100", id: PERCENTS_CONVERT_TO_FRACTION },
// Fractions
{ l: "n1/v2 * n3", r: "(n1 * n3) / v2", id: MULTIPLY_FRACTIONS },
{ l: "v1/n2 * n3", r: "(v1 * n3) / n2", id: MULTIPLY_FRACTIONS },
{ l: "n1/n2 * n3/n4", r: "(n1 * n3) / (n2 * n4)", id: MULTIPLY_FRACTIONS },
{ l: "c1/c2 * c3", r: "(c1 * c3) / c2", id: MULTIPLY_FRACTIONS },
{ l: "n1/n2/n3", r: "n1/(n3*n2)", id: KEMU_REMOVE_DOUBLE_FRACTION },
{ l: "(n1/n2)/n3", r: "n1/(n2*n3)", id: KEMU_REMOVE_DOUBLE_FRACTION },
{ l: "n1/(n2/n3)", r: "n1*(n3/n2)", id: KEMU_REMOVE_DOUBLE_FRACTION },
{ l: "n1/(n2/n3*n4)", r: "(n1 * n3)/(n2 * n4)", id: KEMU_REMOVE_DOUBLE_FRACTION },
// Simplify signs
{ l: "-n1 / (-n2)", r: "n1/n2", id: SIMPLIFY_SIGNS },
{ l: "-c1 / (-c2)", r: "c1/c2", id: SIMPLIFY_SIGNS },
{ l: "n1 / (-n2)", r: "-n1/n2", id: SIMPLIFY_SIGNS },
{ l: "n1 / (-c2)", r: "-n1/c2", id: SIMPLIFY_SIGNS },
{ l: "n1 / ((-n2) * n3)", r: "-n1/(n2 * n3)", id: SIMPLIFY_SIGNS },
{ l: "n1 + n2 * (-n3)", r: "n1 - (n2 * n3)", id: SIMPLIFY_SIGNS },
{ l: "-n1 * (-n2)", r: "n1 * n2", id: SIMPLIFY_SIGNS },
{ l: "-c1 * (-n2)", r: "c1 * n2", id: SIMPLIFY_SIGNS },
{ l: "-(c1/c2*n)", r: "-c1/c2*n", id: SIMPLIFY_SIGNS },
// Add fractions
{ l: "c1 + c3/c2", r: "(c1*c2+c3) / c2", id: ADD_FRACTIONS },
{ l: "c1/c2 + c3/c2", r: "(c1+c3) / c2", id: ADD_FRACTIONS },
// Common denominator
{
l: "c1/c2 + c3/c4",
id: COMMON_DENOMINATOR,
replaceFct: (node, vars) => {
const { c1: num1, c2: denom1, c3: num2, c4: denom2 } = vars;
const lcm = makeConstant(config.default.lcm(denom1.value, denom2.value));
const newNum1 = config.default.equal(denom1.value, lcm.value) ? num1 : makeOp("*", [num1, makeConstant(config.default.divide(lcm.value, denom1.value))]);
const newNum2 = config.default.equal(denom2.value, lcm.value) ? num2 : makeOp("*", [num2, makeConstant(config.default.divide(lcm.value, denom2.value))]);
return makeOp("/", [makeOp("+", [newNum1, newNum2]), lcm]);
}
}
// Pemdas mistakes - This does not work correctly in all cases right now. It is disabled. But this is the current format for making mistakes with custom L values
// { // Added instead of multiplied
// mistakeL: 'c1 + c2 * c3',
// mistakes: [{
// id: 'PEMDAS__ADD_INSTEAD_OF_MULTIPLY',
// replaceFct: (node: any, vars: any) => {
// const added = math.add(vars.c1.value, vars.c2.value)
// const multiplied = makeOp('*', [makeConstant(added), vars.c3])
// return multiplied
// },
// }],
// },
];
_commonPoolOfRules.forEach((rule) => {
if (rule.mistakeL) {
rule.mistakes = rule.mistakes.map((mistake) => {
mistake.l = rule.mistakeL;
if (rule.id && !mistake.id)
mistake.id = rule.id;
return mistake;
});
if (!rule.id)
rule.id = rule.mistakes[0].id;
}
const mistakesForRule = commonRulesMistakes.commonRuleMistakes.filter((mistake) => {
const idAndL = cleanString.cleanString(mistake.placeIn).split("|");
return cleanString.cleanString(rule.id) === idAndL[0] && cleanString.cleanString(rule.l) === idAndL[1];
});
for (const mistake of mistakesForRule) {
if (!rule.mistakes)
rule.mistakes = [];
mistake.l = rule.l;
rule.mistakes.push(mistake);
}
});
const commonPoolOfRules = _commonPoolOfRules;
const commonRules = ruleHelper.createFunctionForEveryRule(commonPoolOfRules);
const commonRulesPooledTogether = (node) => kemuSimplifyCommonServices.applyRules(node, commonPoolOfRules);
exports.commonPoolOfRules = commonPoolOfRules;
exports.commonRules = commonRules;
exports.commonRulesPooledTogether = commonRulesPooledTogether;