java实现字符串四则运算公式解析工具类的方法

作者:零度anngle 时间:2021-11-03 09:22:23 

项目中用到用户定义运算公式进行就算的需求,这样需要进行字符串四则运算解析,下面提供字符串公式四则运算解析与计算工具类,需要的同学可参考。

工具类如下:FormulaCalculator.java:


package org.nercita.bcp.record.util;

import java.util.ArrayList;
import java.util.LinkedList;

/**
* @author zhangwenchao
* @since 2016-08-26
* 公式计算的工具类
*/
public class FormulaCalculator {

private static boolean isRightFormat = true;

public static double getResult(String formula){
double returnValue = 0;
try{
returnValue = doAnalysis(formula);
}catch(NumberFormatException nfe){
System.out.println("公式格式有误,请检查:" + formula);
}catch(Exception e){
e.printStackTrace();
}
if(!isRightFormat){
System.out.println("公式格式有误,请检查:" + formula);
}
return returnValue;
}

private static double doAnalysis(String formula){
double returnValue = 0;
LinkedList<Integer> stack = new LinkedList<Integer>();
int curPos = 0;
String beforePart = "";
String afterPart = "";
String calculator = "";
isRightFormat = true;
while(isRightFormat&&(formula.indexOf('(') >= 0||formula.indexOf(')') >= 0)){
curPos = 0;
for(char s : formula.toCharArray()){
if(s == '('){  
stack.add(curPos);
}else if(s == ')'){  
if(stack.size() > 0){  
beforePart = formula.substring(0, stack.getLast());  
afterPart = formula.substring(curPos + 1);  
calculator = formula.substring(stack.getLast() + 1, curPos);  
formula = beforePart + doCalculation(calculator) + afterPart;  
stack.clear();  
break;  
}else{  
System.out.println("有未关闭的右括号!");  
isRightFormat = false;  
}
}
curPos++;
}
if(stack.size() > 0){
System.out.println("有未关闭的左括号!");
break;
}
}
if(isRightFormat){
returnValue = doCalculation(formula);
}
return returnValue;
}

private static double doCalculation(String formula) {
ArrayList<Double> values = new ArrayList<Double>();
ArrayList<String> operators = new ArrayList<String>();
int curPos = 0;
int prePos = 0;
int minus = 0;
for (char s : formula.toCharArray()) {
if ((s == '+' || s == '-' || s == '*' || s == '/') && minus !=0 && minus !=2) {  
values.add(Double.parseDouble(formula.substring(prePos, curPos).trim()));
operators.add("" + s);
prePos = curPos + 1;
minus = minus +1;
}else{
minus =1;
}
curPos++;
}
values.add(Double.parseDouble(formula.substring(prePos).trim()));
char op;
for (curPos = 0; curPos <= operators.size() - 1; curPos++) {
op = operators.get(curPos).charAt(0);
switch (op) {
case '*':
values.add(curPos, values.get(curPos) * values.get(curPos + 1));
values.remove(curPos + 1);
values.remove(curPos + 1);
operators.remove(curPos);
curPos = -1;
break;
case '/':
values.add(curPos, values.get(curPos) / values.get(curPos + 1));
values.remove(curPos + 1);
values.remove(curPos + 1);
operators.remove(curPos);
curPos = -1;
break;
}
}
for (curPos = 0; curPos <= operators.size() - 1; curPos++) {
op = operators.get(curPos).charAt(0);
switch (op) {
case '+':
values.add(curPos, values.get(curPos) + values.get(curPos + 1));
values.remove(curPos + 1);
values.remove(curPos + 1);
operators.remove(curPos);
curPos = -1;
break;
case '-':
values.add(curPos, values.get(curPos) - values.get(curPos + 1));
values.remove(curPos + 1);
values.remove(curPos + 1);
operators.remove(curPos);
curPos = -1;
break;
}
}
return values.get(0).doubleValue();
}

public static void main(String[] args) {
System.out.println(FormulaCalculator.getResult("3-(4*5)+5"));
System.out.println(FormulaCalculator.getResult("7/2-(-4)"));
System.out.println(FormulaCalculator.getResult("1287763200000-1276272000000")/(3600*24*1000));
}

}

支持四则运算,同时支持负数解析。

另附,小数数据保留位数工具类,SetNumberPrecision.java


package org.nercita.bcp.record.util;

import java.text.DecimalFormat;

/**

* @author zhangwenchao
* 小数点 精度的工具类
*/
public class SetNumberPrecision {

public static String setNumberPrecision(double x,int Number){
String p="#########0";
if(Number==0){
p="#########0";
}else{  
p="#########0.";  
for(int i=0;i<Number;i++){//for的巧妙运用  
p=p+"0";  
}
}  
DecimalFormat f = new DecimalFormat(p);  
String s = f.format(x).toString();  
return s;
}

}

来源:https://blog.csdn.net/zmx729618/article/details/52328377

标签:java,字符串,工具类
0
投稿

猜你喜欢

  • Java Lambda表达式常用的函数式接口

    2021-10-30 13:43:53
  • java身份证合法性校验工具类实例代码

    2022-09-10 18:36:55
  • Spring Boot+Mybatis+Druid+PageHelper实现多数据源并分页的方法

    2023-09-06 19:53:30
  • C语言实现超市计价收款系统

    2021-08-21 17:56:47
  • 程序猿必须要掌握的多线程安全问题之锁策略详解

    2021-10-19 04:57:17
  • 关于fastjson的@JSONField注解的一些问题(详解)

    2021-11-23 09:09:34
  • java开发Dubbo注解Adaptive实现原理

    2022-02-06 11:40:31
  • @GrpcServise 注解的作用和使用示例详解

    2021-07-25 21:12:25
  • Android ScrollView实现下拉弹回动画效果

    2023-04-27 20:31:46
  • springAop实现权限管理数据校验操作日志的场景分析

    2023-11-23 10:00:27
  • JVM分配和回收堆外内存的方式与注意点

    2021-07-25 08:53:34
  • Android App开发中ViewPager组件的入门使用教程

    2023-04-30 21:45:34
  • springboot配置aop切面日志打印过程解析

    2022-07-10 13:14:09
  • C#中的值传递和引用传递详细解析

    2022-03-20 20:11:02
  • C#中Array与ArrayList用法及转换的方法

    2021-07-18 13:13:23
  • Android 实现定时器的四种方式总结及实现实例

    2023-04-20 15:22:04
  • Java8中Optional操作的实际应用

    2022-04-30 22:52:31
  • 详解c# 中的DateTime

    2023-05-15 01:48:58
  • java开发之读写txt文件操作的实现

    2023-11-17 06:00:23
  • JavaWeb使用Cookie模拟实现自动登录功能(不需用户名和密码)

    2021-09-06 00:15:03
  • asp之家 软件编程 m.aspxhome.com