zhangchenglong 2 лет назад
Родитель
Сommit
7d83ef7a1a

+ 1 - 1
src/main/java/com/syjy/calculate/entity/tCalculationFormula.java → src/main/java/com/syjy/calculate/entity/CalculationFormula.java

@@ -21,7 +21,7 @@ import java.util.Date;
  */
 @Data
 @EqualsAndHashCode(callSuper = false)
-public class tCalculationFormula implements Serializable  {
+public class CalculationFormula implements Serializable  {
 
     /**
      * 公式编号(运维标识,主键)

+ 2 - 2
src/main/java/com/syjy/calculate/repository/CalculationFormulaRepository.java

@@ -1,6 +1,6 @@
 package com.syjy.calculate.repository;
 
-import com.syjy.calculate.entity.tCalculationFormula;
+import com.syjy.calculate.entity.CalculationFormula;
 import org.springframework.stereotype.Repository;
 
 import java.util.List;
@@ -19,6 +19,6 @@ public interface CalculationFormulaRepository {
      * @param type 类型
      * @return 返回记录
      */
-    List<tCalculationFormula> findByTypeAndProvince(String type, String provinceEnum);
+    List<CalculationFormula> findByTypeAndProvince(String type, String provinceEnum,String rules);
 
 }

+ 8 - 4
src/main/java/com/syjy/calculate/repository/repositoryImpl/CalculationFormulaRepositoryImpl.java

@@ -1,7 +1,7 @@
 package com.syjy.calculate.repository.repositoryImpl;
 
 import com.syjy.calculate.config.StarterProperties;
-import com.syjy.calculate.entity.tCalculationFormula;
+import com.syjy.calculate.entity.CalculationFormula;
 import com.syjy.calculate.repository.CalculationFormulaRepository;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -89,15 +89,19 @@ public class CalculationFormulaRepositoryImpl implements CalculationFormulaRepos
      * @return
      */
     @Override
-    public List<tCalculationFormula> findByTypeAndProvince(String type, String provinceEnum) {
+    public List<CalculationFormula> findByTypeAndProvince(String type, String provinceEnum,String rules) {
         // 模糊查询参数
         provinceEnum = "%" + provinceEnum + ";%";
         // 查询sql
         String sql = "SELECT * from t_calculation_formula where TYPE = ? and PROVINCE_ENUM like ?  ";
+        if (!"".equals(rules) && rules != null) {
+            rules = "%" + rules + ";%";
+            sql = "SELECT * from t_calculation_formula where TYPE = ? and PROVINCE_ENUM like ? and RULE_FORMULA like ?";
+        }
         // 根据类型和省调查询公式
-        List<tCalculationFormula> calculationFormulaList = new ArrayList<>();
+        List<CalculationFormula> calculationFormulaList = new ArrayList<>();
         try {
-            calculationFormulaList = jdbcTemplate.query(sql, new BeanPropertyRowMapper<>(tCalculationFormula.class), type, provinceEnum);
+            calculationFormulaList = jdbcTemplate.query(sql, new BeanPropertyRowMapper<>(CalculationFormula.class), type, provinceEnum,rules);
         } catch (DataAccessException e) {
             e.printStackTrace();
         }

+ 75 - 30
src/main/java/com/syjy/calculate/service/AccuracyPassRateCalculateService.java

@@ -3,14 +3,12 @@ package com.syjy.calculate.service;
 import com.alibaba.fastjson.JSONArray;
 import com.alibaba.fastjson.JSONObject;
 import com.googlecode.aviator.AviatorEvaluator;
-import com.syjy.calculate.entity.tCalculationFormula;
+import com.syjy.calculate.entity.CalculationFormula;
 import com.syjy.calculate.repository.CalculationFormulaRepository;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
-
 import java.math.BigDecimal;
-import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
@@ -37,25 +35,34 @@ public class AccuracyPassRateCalculateService {
      * @param provinceEnum 省调
      * @param type         短期、超短期
      * @param compare      通过率对比系数
-     * @return 返回Json  result:fail/success  value: 99%  msg:失败及原因
+     * @return 返回Json  result: true/false  value: 99%  msg:失败及原因
      */
     public JSONObject calculate(JSONArray powerData, BigDecimal rl, String provinceEnum, String type, BigDecimal compare) {
         JSONObject jsonResult = new JSONObject();
         jsonResult.put("result", false);
-        // 获取公式
-        List<tCalculationFormula> calculationFormulaList = getCalculationFormulaData(type, provinceEnum);
+        // 对细则进行校验
+        JSONObject checkedJson = checkDataRules(powerData, rl, provinceEnum, type);
+        // 如果细则校验失败,返回细则结果
+        if ("fail".equals(checkedJson.getString("result"))) {
+            jsonResult.put("msg",checkedJson.getString("msg"));
+            return jsonResult;
+        }
+        // 获取细则校验过的数据
+        JSONArray checkedPowerData = checkedJson.getJSONArray("powerData");
+        // 根据类型从数据库中查出公式列表
+        List<CalculationFormula> calculationFormulaList = calculationFormulaRepository.findByTypeAndProvince(type, provinceEnum, null);
         if (calculationFormulaList == null || calculationFormulaList.size() == 0) {
             jsonResult.put("msg", "计算失败,未匹配到公式");
             return jsonResult;
         }
         // 获取功率个数
-        BigDecimal count = BigDecimal.valueOf(powerData.size());
+        BigDecimal count = BigDecimal.valueOf(checkedPowerData.size());
         // 存放每步计算结果
         Map<String, Object> resultMap = new HashMap<>();
         // 公式
         String formula;
         // 循环公式,依次执行公式
-        for (tCalculationFormula calculationFormula : calculationFormulaList) {
+        for (CalculationFormula calculationFormula : calculationFormulaList) {
             BigDecimal formulaResult = ZERO;
             // 获取公式
             formula = calculationFormula.getFormula();
@@ -64,8 +71,8 @@ public class AccuracyPassRateCalculateService {
                 // 获取sum后面的公式
                 formula = formula.split(":")[1];
                 // 循环执行sum后的公式
-                for (int i = 0; i < powerData.size(); i++) {
-                    JSONObject dataJson = powerData.getJSONObject(i);
+                for (int i = 0; i < checkedPowerData.size(); i++) {
+                    JSONObject dataJson = checkedPowerData.getJSONObject(i);
                     // 将执行过的公式结果放入dataMap
                     dataJson.putAll(resultMap);
                     dataJson.put("rl", rl);
@@ -97,9 +104,9 @@ public class AccuracyPassRateCalculateService {
                 }
                 // 非求和计算
             } else {
-                if (powerData.size() > 0) {
+                if (checkedPowerData.size() > 0) {
                     // 获取数据测试
-                    JSONObject dataJson = powerData.getJSONObject(0);
+                    JSONObject dataJson = checkedPowerData.getJSONObject(0);
                     // 将执行过的公式结果放入dataMap
                     dataJson.putAll(resultMap);
                     dataJson.put("rl", rl);
@@ -138,39 +145,77 @@ public class AccuracyPassRateCalculateService {
     }
 
     /**
-     * 获取当前省调的公式列表
-     *
-     * @param type         类型
-     * @param provinceEnum 省调(在数据库中省调存储必须带分号,例如:E12;)
-     * @return
-     */
-    public List<tCalculationFormula> getCalculationFormulaData(String type, String provinceEnum) {
-        List<tCalculationFormula> calculationFormulaList = new ArrayList<>();
-        // 根据类型从数据库中查出公式列表
-        calculationFormulaList = calculationFormulaRepository.findByTypeAndProvince(type, provinceEnum);
-        return calculationFormulaList;
-    }
-
-    /**
      * 过滤结果 <0=0  >100=100
      *
      * @param result 过滤前的结果
      * @return 过滤后的结果
      */
-    private BigDecimal filterResult(BigDecimal result) {
+    public BigDecimal filterResult(BigDecimal result) {
         //当结果为负数时,说明偏差过大,准确率为0
         if (result.compareTo(BigDecimal.ZERO) == -1 || result.compareTo(BigDecimal.ZERO) == 0) {
             result = BigDecimal.ZERO;
         }
-
+        // 如果结果大于1,则准确率设为100
         if (result.compareTo(this.HUNDRED) == 1) {
             result = this.HUNDRED;
         }
         return result;
     }
 
-
-
+    /**
+     * 根据细则过滤数据
+     *
+     * @param powerData
+     * @param rl
+     * @param provinceEnum
+     * @param type
+     * @return
+     */
+    public JSONObject checkDataRules(JSONArray powerData, BigDecimal rl, String provinceEnum, String type) {
+        JSONObject result = new JSONObject();
+        result.put("result", "fail");
+        // 获取细则公式
+        List<CalculationFormula> rulesCalculationFormulaList = calculationFormulaRepository.findByTypeAndProvince(type, provinceEnum, null);
+        // 如果没有细则公式,则不进行细则校验
+        if (rulesCalculationFormulaList == null || rulesCalculationFormulaList.size() == 0) {
+            result.put("result", "success");
+            result.put("powerData", powerData);
+            return result;
+        }
+        JSONArray checkedArray = new JSONArray();
+        JSONObject data = new JSONObject();
+        String checkResult = "";
+        // 循环功率信息
+        for (int i = 0; i < powerData.size(); i++) {
+            String checkFlag = "success";
+            data = powerData.getJSONObject(i);
+            // 循环公式,对每条功率信息进行细则处理
+            for (CalculationFormula formula : rulesCalculationFormulaList) {
+                try {
+                    checkResult = String.valueOf(AviatorEvaluator.execute(formula.getFormula(), data));
+                    if (!"pass".equals(checkResult)) {
+                        checkFlag = "fail";
+                        break;
+                    }
+                } catch (Exception e) {
+                    e.printStackTrace();
+                    log.error("计算公式:" + formula + "错误:" + e.toString());
+                    return result;
+                }
+            }
+            // 如果循环所有规则后还是success,则此条数据校验通过,放入list中
+            if ("success".equals(checkFlag)) {
+                checkedArray.add(data);
+                // 如果没通过,且为单点数据,则返回细则结果
+            } else if (powerData.size() == 1) {
+                result.put("msg", checkResult);
+                return result;
+            }
+        }
+        result.put("result", "success");
+        result.put("powerData", checkedArray);
+        return result;
+    }
 
 }