var ExprCal = { // gramParser :new syntax(), // 用于获取运行实例符号表的传入类 expression :'', // 表达式字符数组 charIndex :0, // 数组下标指针 num :new Array(), // 运算数栈 // 运算符栈关系运算符对应关系 // '<' 对应 < // '>' 对应 > // 'e' 对应 == // 'n' 对应 <> op :new Array(), // 运算符栈 hasReturn :false, genCode :true, // 中间代码临时存放变量 tempIndex :1, // 获取新temp变量名 getTemp : function() { ExprCal.tempIndex++; return "@temp" + ExprCal.tempIndex; }, IsDigit : function(c) { if (c >= '0' && c <= '9') { return true; } return false; }, IsLetter : function(c) { if (c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z') { return true; } return false; }, init : function(expression) { ExprCal.expression = expression; ExprCal.charIndex=0; ExprCal.hasReturn=false; ExprCal.num=new Array(); ExprCal.genCode = !Syntax.InWrite; tempIndex =1; }, Calculate : function() { ExprCal.build(); while (ExprCal.op.length > 0){ ExprCal.calc(); } if (!(ExprCal.hasReturn)) { ExprCal.gen("load", "_", ExprCal.num[ExprCal.num.length - 1], "@result"); } else { ExprCal.gen("load", "_", Syntax.getLastReg(), "@result"); } return 0; }, gen : function(s1, s2, s3, s4) { if (ExprCal.genCode) { Syntax.gen(s1, s2, s3, s4); } }, // 获取下一个字符 getChar : function() { if (ExprCal.charIndex < ExprCal.expression.length) { return ExprCal.expression[ExprCal.charIndex]; } else { return '\0'; } }, // 栈顶运算 calc : function() { var value; var num1, num2; if (ExprCal.op.length == 0) { return; } switch (ExprCal.op[ExprCal.op.length - 1]) { case '<': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("lt", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case '>': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("gt", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case 'e': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("eq", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case 'n': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("ne", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case '+': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("add", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case '-': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("sub", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case '*': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("mul", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; case '/': num1 = ExprCal.num.pop(); num2 = ExprCal.num.pop(); value = ExprCal.getTemp(); ExprCal.gen("div", num2, num1, value); ExprCal.hasReturn = true; ExprCal.num.push(value); break; } ExprCal.op.pop(); }, // 建立数栈和运算符栈 build : function() { var t, tempExpr; var c = ExprCal.getChar(); while (ExprCal.charIndex < ExprCal.expression.length) { // 处理变量 if (ExprCal.IsLetter(c)) { t = ""; tempExpr = ""; // 标识符 while (ExprCal.IsLetter(c) || ExprCal.IsDigit(c) || c == '_') { t += c; ExprCal.charIndex++; c = ExprCal.getChar(); } // 数组下标 if (c == '[') { var level = 1; ExprCal.op.push(c); ExprCal.charIndex++; c = ExprCal.getChar(); while (c != ']' || level != 1) { if (c == '[') { level++; } if (c == ']') { level--; } tempExpr += c; ExprCal.charIndex++; c = ExprCal.getChar(); } ExprCal.init(tempExpr);// ///////////////////////// ExprCal.Calculate(); tempExpr = "[@result]"; } t += tempExpr; ExprCal.num.push(t); } // 处理数字 if (ExprCal.IsDigit(c)) { t = ""; while (ExprCal.IsDigit(c) || c == '.') { t += c; ExprCal.charIndex++; c = ExprCal.getChar(); } ExprCal.num.push(parseFloat(t)); } // 处理运算符 switch (c) { case '(': ExprCal.op.push(c); break; case ')': while (ExprCal.op[ExprCal.op.length - 1] != '(') { ExprCal.calc(); } ExprCal.op.pop(); break; case '>': // > 运算 if (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '<' || ExprCal.op[ExprCal.op.length - 1] == 'e' || ExprCal.op[ExprCal.op.length - 1] == 'n' || ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push('>'); break; case '=': // == 运算 ExprCal.charIndex++; if (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '<' || ExprCal.op[ExprCal.op.length - 1] == '>' || ExprCal.op[ExprCal.op.length - 1] == 'n' || ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push('e'); break; case '<': if (ExprCal.expression[ExprCal.charIndex + 1] != '>') // > 运算 { if (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '>' || ExprCal.op[ExprCal.op.length - 1] == 'e' || ExprCal.op[ExprCal.op.length - 1] == 'n' || ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push('<'); } else // <> 运算 { ExprCal.charIndex++; if (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '<' || ExprCal.op[ExprCal.op.length - 1] == '>' || ExprCal.op[ExprCal.op.length - 1] == 'e' || ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push('n'); } break; case '+': while (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push(c); break; case '-': while (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '+' || ExprCal.op[ExprCal.op.length - 1] == '-' || ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push(c); break; case '*': while (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push(c); break; case '/': while (ExprCal.op.length > 0 && (ExprCal.op[ExprCal.op.length - 1] == '*' || ExprCal.op[ExprCal.op.length - 1] == '/')) { ExprCal.calc(); } ExprCal.op.push(c); break; default: ExprCal.charIndex++; c = ExprCal.getChar(); continue; } ExprCal.charIndex++; c = ExprCal.getChar(); } } }