首页 > 解决方案 > 将另一个对象的属性作为参数的 Javascript 对象以某种方式更改它

问题描述

我一直在做一个数学解析器项目。我快完成了,但我遇到了一个我找不到原因的问题。

我有 3 个 javascript 文件:

main.js

var button1 = document.getElementById("button");
var text1 = document.getElementById("text");
var output = document.getElementById("result");

button1.addEventListener("click", function(){

    var textInput = text1.value;
    var cleared = new clearingUnwantedCharacters(textInput);
    var marked = new subgroupMarking(cleared.output);
    var prioritizedList = new subgroupPrioritization(marked.parenGroups);
    for(var i = 0; i <= 360; i++){
        var splittedPieces = new splittingOperators(prioritizedList.prioritizedGroups);
        var calculatedPieces = new calculatePieces(splittedPieces.seperatedPieces, i, true);
        console.log(calculatedPieces.result);
    }

});

对象.js

function clearingUnwantedCharacters(inputText){
    this.output = inputText;
    this.output = this.output.replace(/\s+/g, '');
    this.output = this.output.toLowerCase();
}

function subgroupMarking(inputText){    
    this.parenGroups = [inputText];

    this.locLeftParen = markChar(this.parenGroups[0], "(");
    this.locRigthParen = markChar(this.parenGroups[0], ")");        

    for(var i = this.locLeftParen.length-1; i >= 0; i--){ 
        var leftParen = this.locLeftParen[i];
        var rightParen = this.locRigthParen.find(function(res){return res > leftParen});
        this.parenGroups[i+1] = this.parenGroups[0].substring(leftParen+1, rightParen);
        this.parenGroups[0] = changeAt(this.parenGroups[0], leftParen, rightParen+1, "{_"+(i+1)+"}");
        this.locLeftParen = markChar(this.parenGroups[0], "(");
        this.locRigthParen = markChar(this.parenGroups[0], ")");
    }
}

function subgroupPrioritization(subgroupList){  
    var withParenGroup = [];
    var withoutParenGroup = [];

    for(var i = 0; i < subgroupList.length; i++){ 
        var content = subgroupList[i].toString();
        var hasParenGroup = content.search(/{_\d+}/g);  
        if(hasParenGroup == -1){
            withoutParenGroup.push(content);
        }else{
            withParenGroup.push(content);
        }

    }

    this.prioritizedGroups = withParenGroup.concat(withoutParenGroup);
}

function splittingOperators(prioritizedGroupList){
    this.seperatedPieces = [];

    for(var i = prioritizedGroupList.length-1; i >= 0; i--){
        var pieces = prioritizedGroupList[i].split(/(\+|\*|\/|\^|\b(?=-)|(?<=})(?=-))/g);

        for(var k = 0; k < pieces.length; k++){
                if(pieces[k] == ""){
                    pieces[k] = "+";
                }
        }

        this.seperatedPieces.unshift(pieces);

    }
}

function calculatePieces(pieceList, x, degreeOption){

    this.result = pieceList;

    for(var i = this.result.length-1; i >= 0; i--){ // ["34", "+", "2{_2}"] 
            for(var k = 0; k < this.result[i].length; k++){ // 34, +, 2{_2} 
                var specialFlag = false;
                var totalMultiplication = (countChar(this.result[i][k], "-")%2 == 0) ? 1 : -1;  
                var has = {
                    x : this.result[i][k].includes("x"),
                    subgroup : (this.result[i][k].search(/{_\d+}/g) != -1),
                    logarithm : this.result[i][k].includes("log"),
                    trigonometry : (this.result[i][k].includes("sin") || this.result[i][k].includes("cos") || this.result[i][k].includes("tan") || this.result[i][k].includes("cot"))
                };
                if(has.trigonometry){
                    specialFlag = true;

                    var trigSubgroupIndexes = [];
                    var trigTypes = [];

                    var trigsMultiplied = 1;

                    this.result[i][k] = this.result[i][k].replace(/(?:arc)?(sin|cos|tan|cot){_(\d+)}/g, function(match, type, index){
                        trigSubgroupIndexes.push(parseInt(index));
                        if(match.includes("arc")){                      
                            trigTypes.push([true, type]);
                        }else{
                            trigTypes.push([false, type]);
                        }   
                        return " ";
                    }); 
                    for(var l = 0; l < trigTypes.length; l++){                  
                        var inverseness = trigTypes[l][0];
                        var type = trigTypes[l][1];
                        var parameter = (degreeOption) ? convertToRadian(parseFloat(this.result[trigSubgroupIndexes[l]])) : parseFloat(this.result[trigSubgroupIndexes[l]]);
                        var result;
                        if(inverseness){
                            switch(type){
                                case "sin":
                                    result = Math.asin(parameter);
                                break;case "cos":
                                    result = Math.acos(parameter);
                                break;case "tan":
                                    result = Math.atan(parameter);
                                break;case "cot":
                                    result = 1 / Math.atan(parameter);
                                break;
                            }
                        }else{
                            switch(type){
                                case "sin":
                                    result = Math.sin(parameter);
                                break;case "cos":
                                    result = Math.cos(parameter);
                                break;case "tan":
                                    result = Math.tan(parameter);
                                break;case "cot":
                                    result = 1 / Math.tan(parameter);
                                break;
                            }
                        }
                        trigsMultiplied *= result;
                    }                   
                    totalMultiplication *= trigsMultiplied;
                }
                if(has.logarithm){
                    specialFlag = true;
                    var logSubgroupIndexes = [];
                    var logsMultiplied = 1;
                    this.result[i][k] = this.result[i][k].replace(/log{_(\d+)}{_(\d+)}/g, function(match, firstIndex, secondIndex){
                        logSubgroupIndexes.push([parseInt(firstIndex), parseInt(secondIndex)]);
                        return " ";
                    });
                    for(var l = 0; l < logSubgroupIndexes.length; l++){                 
                        var base = this.result[logSubgroupIndexes[l][0]];
                        var power = this.result[logSubgroupIndexes[l][1]];
                        logsMultiplied *= (Math.log(power) / Math.log(base));
                    }                   
                    totalMultiplication *= logsMultiplied;
                }
                if(has.subgroup){
                    specialFlag = true;
                    var subgroupIndexes = [];
                    var groupsMultiplied = 1;                   
                    this.result[i][k] = this.result[i][k].replace(/{_(\d+)}/g, function(match, index){
                        subgroupIndexes.push(parseInt(index));
                        return " ";
                    });
                    for(var l = 0; l < subgroupIndexes.length; l++){                    
                        groupsMultiplied *= this.result[subgroupIndexes[l]];
                    }
                    totalMultiplication *= groupsMultiplied;
                }
                if(has.x){
                    specialFlag = true;
                    var powerX = countChar(this.result[i][k], "x");
                    this.result[i][k] = this.result[i][k].replace("x", " ");
                    totalMultiplication *= Math.pow(x, powerX);
                }
                if(specialFlag == true){
                    var factors = this.result[i][k].match(/\d+/g);
                    if(factors !== null){
                        for(var l = 0; l < factors.length; l++){
                            totalMultiplication *= parseFloat(factors[l]);
                        }
                    }
                    if(!isFinite(totalMultiplication) || checkNum(this.result[i][k]) || this.result[i][k].includes("(") || this.result[i][k].includes(")")){
                        this.result[i][k] = NaN;                        
                    }else{
                        this.result[i][k] = totalMultiplication;
                    }
                }


            }

            var operators = ["^","*","/","+","-"];      
            for(var k = 0; k < operators.length; k++){
                var search = this.result[i].indexOf(operators[k]);

                while(search != -1){
                    switch(operators[k]){
                        case "+":   
                            this.result[i].splice(search-1, 3, checkParse(this.result[i][search-1]) + checkParse(this.result[i][search+1]));
                        break;case "-":
                            this.result[i].splice(search-1, 3, checkParse(this.result[i][search-1]) - checkParse(this.result[i][search+1]));
                        break;case "*":
                            this.result[i].splice(search-1, 3, checkParse(this.result[i][search-1]) * checkParse(this.result[i][search+1]));
                        break;case "/":
                            this.result[i].splice(search-1, 3, checkParse(this.result[i][search-1]) / checkParse(this.result[i][search+1]));
                        break;case "^":
                            this.result[i].splice(search-1, 3, Math.pow(checkParse(this.result[i][search-1]) , checkParse(this.result[i][search+1])));
                        break;
                    }   
                    if(this.result[i].indexOf(operators[k], search) == -1){                     
                        break;
                    }else{
                        search = this.result[i].indexOf(operators[k], search);      
                    }
                }
            }   
    }
    if(isNaN(this.result[0][0])){
        this.result = "An error has occured, please make sure the parameters are correct.";
    }else{
        this.result = this.result[0][0];
    }
}

函数.js

function countChar(str, character){
    return str.toString().split(character).length-1;
}
function markChar(str, character){

    var charCount = str.split(character).length;
    var result = [];

    for(var i = 0; i < charCount - 1; i++){
        if(result.length == 0){
            result.push(str.indexOf(character));
        }else{
            result.push(str.indexOf(character, result[i-1] + 1));
        }   
    }
    return result;
}
function changeAt(str, startingIndex, endingIndex, replacement){ // Returns the given string with the part between startingIndex and endingIndex replaced with replacement.
    return str.substring(0, startingIndex) + replacement + str.substring(endingIndex, str.length);  
}
function checkParse(str){
    if(/[a-z]/.test(str) || countChar(str, ".") > 1){
        return NaN;
    }else{
        return parseFloat(str);
    }
}
function checkNum(str){
    return (/[a-z]/.test(str) || countChar(str, ".") > 1);
}
function convertToRadian(degrees) {

    return degrees * Math.PI / 180;
}

像上面那样完成后,它会按预期工作。它根据 main.js 中的 for 循环中指定的范围将值放入 x 并在 console.logs 中记录结果。但是我不想每次使用另一个 x 值重新计算时都创建 splitOperators 对象。这是不必要的,因为实际公式保持不变。

var button1 = document.getElementById("button");
var text1 = document.getElementById("text");
var output = document.getElementById("result");

button1.addEventListener("click", function(){

    var textInput = text1.value;
    var cleared = new clearingUnwantedCharacters(textInput);
    var marked = new subgroupMarking(cleared.output);
    var prioritizedList = new subgroupPrioritization(marked.parenGroups);
    var splittedPieces = new splittingOperators(prioritizedList.prioritizedGroups);
    for(var i = 0; i <= 360; i++){
        var calculatedPieces = new calculatePieces(splittedPieces.seperatedPieces, i, true);
        console.log(calculatedPieces.result);
    }

});

当我将对象创建放在 for 循环之外时,它会计算并记录第一个 x 值,但它给出了

未捕获的类型错误:this.result[i][k].includes 不是函数

之后作为错误。我怀疑这是因为它splittedPieces.seperatedPieces在不应该改变的时候改变了。我找不到任何理由让它这样做,或者我可能遗漏了一些东西。

标签: javascriptobjectparametersproperties

解决方案


推荐阅读