java代码执⾏字符串中的逻辑运算⽅法
⽅式⼀
public class Test
{
public static void main(String[] args) throws Exception {
String str = "(a or b) and c";
str = placeAll("or", "||");
str = placeAll("and", "&&");
System.out.println(str);
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = EngineByName("js");
engine.put("a",true);
engine.put("b",false);
engine.put("c",true);
Object result = engine.eval_r(str);
System.out.println("结果类型:" + Class().getName() + ",计算结果:" + result);
}
}
这种⽅式使⽤js的⽅式进⾏运算,使⽤较简单,但是当运算double类型的四则运算时结果会出现循环⼩数,运算结果会出现问题.
⽅式⼆(能够保证四则运算精度):
/**
* @Project: BizRule
* @File: ffeesweet.util.MathExpress.java
* @Author: coffeesweet
* @Date: 2011-3-28
* @Description: 2011 coffeesweet Inc. All rights reserved.
*/
ffeesweet.util;
import java.math.BigDecimal;
import java.math.MathContext;
import java.math.RoundingMode;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.StringTokenizer;
import Matcher;
import Pattern;
/**
* @author coffeesweet
* +,-,*,/四则运算的表达式逆波兰解析计算类,精确计算,应⽤BigDecimal类处理
* ⽀持负数,但规范除整个表达式第⼀个数为负数时可以不出现在'('后,其它表达式中间任何位置的
* 负数必须出现在'('后,即:⽤括号括起来。⽐如:-3+(-2+1)*10或-3+((-2)+1)*10或(-3)+(-2+1)*10或(-3)+((-2)+1)*10
*/
indexof空格算不算public class MathExpress {
/**
* +
*/
private final static String OP1 = "+";
/**
* -
*/
private final static String OP2 = "-";
/**
* *
*/
private final static String OP3 = "*";
/**
* /
*/
private final static String OP4 = "/";
/**
* ^
*/
// private final static String OP5 = "^";
/**
* %
*/
// private final static String OP6 = "%";
/**
* (
*/
private final static String OPSTART = "(";
/**
* )
*/
private final static String OPEND = ")";
/**
* !⽤来替代负数前⾯的'-'
*/
// private final static String NEGATIVESING = "!";
/**
* !⽤来替代负数前⾯的'+'
*/
// private final static String PLUSSING = "@";
/**
* '#'⽤来代表运算级别最低的特殊字符
*/
// private final static String LOWESTSING = "#";
/
/最原始的四则运算式
private String expBase;
//经过初始化处理后的四则运算式
private String expInited;
//精度
private int precision=10;
//取舍模式
private RoundingMode roundingMode=RoundingMode.HALF_UP;
//精度上下⽂
private MathContext mc;
//四则运算解析
private List<String> expList = new ArrayList<String>();
//存放逆波兰表达式
private List<String> rpnList = new ArrayList<String>();
public MathExpress(){
}
public MathExpress(String expBase) {
init(expBase,this.undingMode);
}
public MathExpress(String expBase,int precision,RoundingMode roundingMode){ init(expBase,precision,roundingMode);
}
public void init(String expBase,int precision,RoundingMode roundingMode){
this.precision = precision;
< = new MathContext(precision,roundingMode);
StringTokenizer st = new pInited,"+-*/^%()",true);
while(st.hasMoreElements()){
}
this.rpnList = pList);
}
/
**
* @return the expBase
*/
public String getExpBase() {
return expBase;
}
/**
* @param expBase the expBase to set
*/
public void setExpBase(String expBase) {
}
/**
* @return the expInited
*/
public String getExpInited() {
return expInited;
}
/**
* @param expInited the expInited to set
*/
public void setExpInited(String expInited) {
}
/**
* @return the precision
*/
public int getPrecision() {
return precision;
}
/**
* @param precision the precision to set
*/
public void setPrecision(int precision) {
this.precision = precision;
}
/**
* @return the roundingMode
*/
public RoundingMode getRoundingMode() {
return roundingMode;
}
/**
* @param roundingMode the roundingMode to set
*/
public void setRoundingMode(RoundingMode roundingMode) { undingMode = roundingMode;
}
/**
* @return the expList
*/
public List<String> getExpList() {
return expList;
}
/**
* @param expList the expList to set
*/
public void setExpList(List<String> expList) {
}
/**
* @return the rpnList
*/
public List<String> getRpnList() {
return rpnList;
}
/**
* @param rpnList the rpnList to set
*/
public void setRpnList(List<String> rpnList) {
this.rpnList = rpnList;
}
/**
* @return the mc
*/
public MathContext getMc() {
return mc;
}
/
**
* @param mc the mc to set
*/
public void setMc(MathContext mc) {
< = mc;
}
/**
* 去除空⽩字符和在负号'-'前加'0',便于后⾯的StringTokenizer * @param exp
* @return
*/
private static String initExpress(String exp){
String reStr = null;
reStr = placeAll("\\s", "");
if(reStr.startsWith("-")){
reStr = "0"+reStr;
}
reStr = placeAll("\\(\\-", "(0-");
return reStr;
}
/**
* 是否是整数或是浮点数,但默认-05.15这种也认为是正确的格式 * @param str
* @return
*/
private boolean isNumber(String str){
Pattern p = Patternpile("^(-?\\d+)(\\.\\d+)?$");
Matcher m = p.matcher(str);
boolean isNumber = m.matches();
return isNumber;
}
/**
* 设置优先级顺序()设置与否⽆所谓
* @param sign
* @return
*/
private int precedence(String str){
char sign = str.charAt(0);
switch(sign){
case '+':
case '-':
return 1;
case '*':
case '/':
return 2;
case '^':
case '%':
return 3;
case '(':
case ')':
// case '#':
default:
return 0;
}
}
/**
* 转变为逆波兰表达式
* @param strList
* @return
*/
public List<String> initRPN(List<String> strList){
List<String> returnList = new ArrayList<String>();
//⽤来存放操作符的栈
Stack stack = new Stack();
// stack.push(LOWESTSING);
int length = strList.size();
for(int i=0;i<length;i++ ){
String str = (i);
if(isNumber(str)){
returnList.add(str);
}else{
if(str.equals(OPSTART)){
//'('直接⼊栈
stack.push(str);
}else if(str.equals(OPEND)){
//')'
//进⾏出栈操作,直到栈为空或者遇到第⼀个左括号
while (!stack.isEmpty()) {
//将栈顶字符串做出栈操作
String tempC = stack.pop();
if (!tempC.equals(OPSTART)) {
//如果不是左括号,则将字符串直接放到逆波兰链表的最后 returnList.add(tempC);
}else{
//如果是左括号,退出循环操作
break;
}
}
}else{
if (stack.isEmpty()) {
//如果栈内为空
/
/将当前字符串直接压栈
stack.push(str);
}else{
//栈不空,⽐较运算符优先级顺序
if(p())>=precedence(str)){
//如果栈顶元素优先级⼤于当前元素优先级则
while(!stack.isEmpty() && p())>=precedence(str)){
returnList.add(stack.pop());
}
}
stack.push(str);
}
}
}
}
//如果栈不为空,则将栈中所有元素出栈放到逆波兰链表的最后
while (!stack.isEmpty()) {
returnList.add(stack.pop());
}
return returnList;
}
/**
* 计算逆波兰表达式
* @param rpnList
* @return
*/
public String caculate(List<String> rpnList){
Stack numberStack = new Stack();
int length=rpnList.size();
for(int i=0;i<length;i++){
String (i);
if(isNumber(temp)){
numberStack.push(temp);
}else{
BigDecimal tempNumber1 = new BigDecimal(numberStack.pop(),);
BigDecimal tempNumber2 = new BigDecimal(numberStack.pop(),);
BigDecimal tempNumber = new BigDecimal("0",);
if(temp.equals(OP1)){
tempNumber=tempNumber2.add(tempNumber1);
}else if(temp.equals(OP2)){
tempNumber=tempNumber2.subtract(tempNumber1);
}else if(temp.equals(OP3)){
tempNumber=tempNumber2.multiply(tempNumber1);
}else if(temp.equals(OP4)){
tempNumber=tempNumber2.divide(tempNumber1,
precision,
roundingMode);
}
numberStack.String());
}
}
return numberStack.pop();
}
/**
* 按照类的缺省参数进⾏计算
* @return
*/
public String caculate(){
return caculate(this.rpnList);
}
/**
* 数字条件表达式精确⽐较
* eg: "3.0>2" "1<5" "1==5" "1!=5" "(1.0+2)>3" "((-0.9+3)>=2. 1)"
* 不⽀持&&,||等连接符
* @param str
* @return
*/
public static boolean compareTo(String strParm){
boolean reBoolean = false;
boolean isParentheses = false;//标记是否有()括上整个字符串
String str = initExpress(strParm);
Pattern p = Patternpile("^\\([\\s\\S]*\\)$");
Matcher m = p.matcher(str);
isParentheses = m.matches();
if(-1==str.indexOf(">=")&&-1==str.indexOf("<=")&&-1==str.indexOf("==")&&-1==str.indexOf("!=")){ if(-1==str.indexOf(">")&&-1==str.indexOf("<"))
throw new IllegalArgumentException("异常:条件表达式不正确!");
}
if(-1 != str.indexOf(">=")){
String[] strTemps = str.split(">=");
if(isParentheses){
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论