📄 expressionanalyze.java
字号:
break;
}
}
if(!findThird)
throw new Exception ("there are not so much variables,the value '"
+ value3 + "' is not needed");
}
//以下是表达式求值的算符优先算法。公式以"#"做结束符。
//设optr和opnd分别为运算符栈和操作数栈
Stack optr = new Stack(); //存储操作符的栈
Stack opnd = new Stack(); //存储操作数的栈
optr.push("#");
current = elemList;
while(!(current.data.equals("#") && optr.top().equals("#"))){
//如果不是运算符,则直接入操作数栈
if(!current.isOperator){
opnd.push(current.data);
current = current.next;
}
else{
int indexOfFirst = 0,indexOfLast = 0;
boolean flagOfFirst = false,flagOfLast = false;
for(int i = 0;i < keywords.length;i++){
if(optr.top().equals(keywords[i])){
indexOfLast = i;
flagOfLast = true;
}
if(current.data.equals(keywords[i])){
indexOfFirst = i;
flagOfFirst = true;
}
if(flagOfLast && flagOfFirst)
break;
}
if(!flagOfLast)
throw new Exception ("the operator '" + optr.top()
+ "' is not supported");
if(!flagOfFirst)
throw new Exception ("the operator '" + current.data
+ "' is not supported");
flagOfLast = false;
flagOfFirst = false;
switch(PRI[indexOfLast][indexOfFirst]){
case '<' ://栈顶元素优先级低
optr.push(current.data);
current = current.next;
break;
case '=' ://脱括弧、计算单目运算并接受下一个字符串
optr.pop();
current = current.next;
boolean isOptr = false;
for(int i = 0;i < keywords.length;i++)
if(optr.top().equals(keywords[i])){
if(keywords[i].length() > 1)
isOptr = true;
break;
}
if(!isOptr)
break;
isOptr = false;
//强制类型转换,若转换不成功则说明是变量
try {
firstDouTemp = Double.parseDouble(opnd.top());
}
catch (NumberFormatException e){
if(opnd.top().equals(firstStr))
firstDouTemp = firstDou;
else if(opnd.top().equals(secondStr))
firstDouTemp = secondDou;
else if(opnd.top().equals(thirdStr))
firstDouTemp = thirdDou;
else
throw new Exception ("the value of '" + opnd.top()
+ "' is not found");
}
opnd.pop();
if(optr.top().equals("abs"))
opnd.push(new Double(Math.abs(firstDouTemp)).toString());
else if(optr.top().equals("acos")){
if(Math.abs(firstDouTemp) > 1)
throw new Exception("the absolute value of the argument '"
+ firstDouTemp + "' that 'acos' takes is greater than 1");
opnd.push(new Double(Math.acos(firstDouTemp)).toString());
}
else if(optr.top().equals("asin")){
if(Math.abs(firstDouTemp) > 1)
throw new Exception("the absolute value of the argument '"
+ firstDouTemp + "' that 'asin' takes is greater than 1");
opnd.push(new Double(Math.asin(firstDouTemp)).toString());
}
else if(optr.top().equals("atan"))
opnd.push(new Double(Math.atan(firstDouTemp)).toString());
else if(optr.top().equals("cbrt"))
opnd.push(new Double(Math.cbrt(firstDouTemp)).toString());
else if(optr.top().equals("cos"))
opnd.push(new Double(Math.cos(firstDouTemp)).toString());
else if(optr.top().equals("cosh"))
opnd.push(new Double(Math.cosh(firstDouTemp)).toString());
else if(optr.top().equals("ceil"))
opnd.push(new Double(Math.ceil(firstDouTemp)).toString());
else if(optr.top().equals("exp"))
opnd.push(new Double(Math.exp(firstDouTemp)).toString());
else if(optr.top().equals("expm1"))
opnd.push(new Double(Math.expm1(firstDouTemp)).toString());
else if(optr.top().equals("floor"))
opnd.push(new Double(Math.floor(firstDouTemp)).toString());
else if(optr.top().equals("log")){
if(firstDouTemp < 0)
throw new Exception("the argument '" + firstDouTemp
+ "' that 'log' takes is less than zero");
opnd.push(new Double(Math.log(firstDouTemp)).toString());
}
else if(optr.top().equals("log10")){
if(firstDouTemp < 0)
throw new Exception("the argument '" + firstDouTemp
+ "' that 'log10' takes is less than zero");
opnd.push(new Double(Math.log10(firstDouTemp)).toString());
}
else if(optr.top().equals("log1p")){
if(firstDouTemp < -1)
throw new Exception("the argument '" + firstDouTemp
+ "' that 'log1p' takes is less than -1");
opnd.push(new Double(Math.log1p(firstDouTemp)).toString());
}
else if(optr.top().equals("rint"))
opnd.push(new Double(Math.rint(firstDouTemp)).toString());
else if(optr.top().equals("round"))
opnd.push(new Double(Math.round(firstDouTemp)).toString());
else if(optr.top().equals("signum"))
opnd.push(new Double(Math.signum(firstDouTemp)).toString());
else if(optr.top().equals("sin"))
opnd.push(new Double(Math.sin(firstDouTemp)).toString());
else if(optr.top().equals("sinh"))
opnd.push(new Double(Math.sinh(firstDouTemp)).toString());
else if(optr.top().equals("sqrt")){
if(firstDouTemp < 0)
throw new Exception("the argument '" + firstDouTemp
+ "' that 'sqrt' takes is less than zero");
opnd.push(new Double(Math.sqrt(firstDouTemp)).toString());
}
else if(optr.top().equals("tan"))
opnd.push(new Double(Math.tan(firstDouTemp)).toString());
else if(optr.top().equals("tanh"))
opnd.push(new Double(Math.tanh(firstDouTemp)).toString());
else if(optr.top().equals("toDegrees"))
opnd.push(new Double(Math.toDegrees(firstDouTemp)).toString());
else if(optr.top().equals("toRadians"))
opnd.push(new Double(Math.toRadians(firstDouTemp)).toString());
else
throw new Exception ("the operator '" + optr.top()
+ "' is not supported");
optr.pop();
break;
case '@' ://表达式输入有误
throw new Exception ("the operators '" + keywords[indexOfLast]
+ "' and '" + keywords[indexOfFirst]
+ "' are not matched");
case '>' ://站定元素优先级高、计算双目运算
//强制类型转换,若转换不成功则说明是变量
try {
secondDouTemp = Double.parseDouble(opnd.top());
}
catch (NumberFormatException e){
if(opnd.top().equals(firstStr))
secondDouTemp = firstDou;
else if(opnd.top().equals(secondStr))
secondDouTemp = secondDou;
else if(opnd.top().equals(thirdStr))
firstDouTemp = thirdDou;
else
throw new Exception ("the value of '" + opnd.top()
+ "' is not found");
}
opnd.pop();
//强制类型转换,若转换不成功则说明是变量
try {
firstDouTemp = Double.parseDouble(opnd.top());
}
catch (NumberFormatException e){
if(opnd.top().equals(firstStr))
firstDouTemp = firstDou;
else if(opnd.top().equals(secondStr))
firstDouTemp = secondDou;
else if(opnd.top().equals(thirdStr))
firstDouTemp = thirdDou;
else
throw new Exception ("the value of '" + opnd.top()
+ "' is not found");
}
opnd.pop();
if(optr.top().equals("+")){
opnd.push(new Double(firstDouTemp + secondDouTemp).toString());
}
else if(optr.top().equals("-")){
opnd.push(new Double(firstDouTemp - secondDouTemp).toString());
}
else if(optr.top().equals("*")){
opnd.push(new Double(firstDouTemp * secondDouTemp).toString());
}
else if(optr.top().equals("/")){
if(secondDouTemp == 0)
throw new Exception ("the second argument that '/' takes is 0");
opnd.push(new Double(firstDouTemp / secondDouTemp).toString());
}
else if(optr.top().equals("%")){
if(secondDouTemp == 0)
throw new Exception ("the second argument that '%' takes is 0");
opnd.push(new Double(firstDouTemp % secondDouTemp).toString());
}
else
throw new Exception ("the operator '" + optr.top()
+ "' is not supported");
optr.pop();
break;
}
}
}
result = Double.parseDouble(opnd.pop());
}
public Double getResult(){
return result;
}
private String firstStr;//存储公式中第一个变量的表达式
private String secondStr;//存储公式中第二个变量的表达式
private String thirdStr;//存储公式中第三个变量的表达式
private double firstDou;//存储公式中第一个变量的值
private double secondDou;//存储公式中第二个变量的值
private double thirdDou;//存储公式中第三个变量的值
private double value1;//从构造函数接收过来的第一个变量得值
private double value2;//从构造函数接收过来的第二个变量得值
private double value3;//从构造函数接收过来的第三个变量得值
private double firstDouTemp;//存储每次计算的第一个临时变量
private double secondDouTemp;//存储每次计算的第二个变量
private ElemList elemList = null;//链表头
private ElemList current = null;//链表当前指针
private int numOfParameter; //公式中变量的个数
private String expr;//存储公式
private double result;//最终的计算结果
//运算符
private static final String [] keywords =
{
"+","-","*","/","(",")","%","abs","acos","asin","atan","cbrt","ceil",
"cos","cosh","exp","expm1","floor","log","log10","log1p","rint","round",
"signum","sin","sinh","sqrt","tan","tanh","toDegrees","toRadians","#"
};
//运算符优先级
private static final char [] [] PRI =
{ // + - * / ( ) % abs acos asin atan cbrt ceil cos cosh exp expm1 floor log log10 log1p rint round signum sin sigh sprt tan tanh toDegrees toRadians #
/* + */{'>','>','<','<','<','>','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '>'},
/* - */{'>','>','<','<','<','>','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '>'},
/* * */{'>','>','>','>','<','>','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '>'},
/* / */{'>','>','>','>','<','>','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '>'},
/* ( */{'<','<','<','<','<','=','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '@'},
/* ) */{'>','>','>','>','@','>','>','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '>'},
/* % */{'>','>','>','>','<','>','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '>'},
/* abs */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* acos */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* asin */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* cbrt */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* ceil */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* acos */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* cos */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* cos */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* exp */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* expm1*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* floor*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* log */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* log10*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* log1p*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* rint*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* round*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/*signum*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* sin */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* sinh */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* sprt*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* tan */{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* tanh*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/*toDegrees*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/*toRadians*/{'@','@','@','@','<','@','@','@', '@', '@','@', '@', '@', '@','@', '@','@', '@', '@','@', '@', '@', '@', '@', '@','@', '@', '@','@', '@', '@', '@'},
/* # */{'<','<','<','<','<','@','<','<', '<', '<','<', '<', '<', '<','<', '<','<', '<', '<','<', '<', '<', '<', '<', '<','<', '<', '<','<', '<', '<', '='}
};
}
//将公式中关键字和其他量分开存放的链式结构
class ElemList {
ElemList (String value) {
data = value;
}
ElemList next;
String data;
boolean isOperator;
}
//Stack类中用到的链式结构
class ListElement {
ListElement (String value){
data = value;
}
ListElement next;
String data;
}
//--栈类
class Stack{
//返回栈顶元素的data域
public String top(){
if(top != null)
return top.data;
else
return null;
}
//将新元素压入栈
public void push(String value){
if(top == null)
top = new ListElement(value);
else{
ListElement temp = new ListElement(value);
temp.next = top;
top = temp;
}
}
//弹出栈顶元素并返回其data域
public String pop(){
String result = top();
if(top != null)
top = top.next;
return result;
}
//判断栈是否为空
public boolean empty(){
return top == null;
}
private ListElement top = null;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -