base_from_predict.go 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212
  1. package services
  2. import (
  3. "errors"
  4. "eta_gn/eta_index_lib/models"
  5. "eta_gn/eta_index_lib/utils"
  6. "fmt"
  7. "github.com/dengsgo/math-engine/engine"
  8. "github.com/shopspring/decimal"
  9. "strconv"
  10. "strings"
  11. "time"
  12. )
  13. func GetCalculateByRuleByNineParams(req models.RuleConfig) (formula string, edbInfoList []*models.EdbInfo, edbInfoIdBytes []string, err error, errMsg string) {
  14. formula = req.Value
  15. formula = strings.Replace(formula, "(", "(", -1)
  16. formula = strings.Replace(formula, ")", ")", -1)
  17. formula = strings.Replace(formula, ",", ",", -1)
  18. formula = strings.Replace(formula, "。", ".", -1)
  19. formula = strings.Replace(formula, "%", "*0.01", -1)
  20. var checkFormulaStr string
  21. for _, tmpEdbInfoId := range req.EdbInfoIdArr {
  22. checkFormulaStr += tmpEdbInfoId.FromTag + ","
  23. edbInfoIdBytes = append(edbInfoIdBytes, tmpEdbInfoId.FromTag)
  24. }
  25. formulaSlice, err := utils.CheckFormulaJson(formula)
  26. if err != nil {
  27. errMsg = "公式格式错误,请重新填写"
  28. err = errors.New(errMsg)
  29. return
  30. }
  31. for _, f := range formulaSlice {
  32. formulaMap, e := utils.CheckFormula(f)
  33. if e != nil {
  34. err = fmt.Errorf("公式错误,请重新填写")
  35. return
  36. }
  37. for _, v := range formulaMap {
  38. if !strings.Contains(checkFormulaStr, v) {
  39. errMsg = "公式错误,请重新填写"
  40. err = errors.New(errMsg)
  41. return
  42. }
  43. }
  44. }
  45. edbInfoList = make([]*models.EdbInfo, 0)
  46. for _, tmpEdbInfoId := range req.EdbInfoIdArr {
  47. fromEdbInfo, tmpErr := models.GetEdbInfoById(tmpEdbInfoId.EdbInfoId)
  48. if tmpErr != nil {
  49. if tmpErr.Error() == utils.ErrNoRow() {
  50. err = errors.New("指标 " + strconv.Itoa(tmpEdbInfoId.EdbInfoId) + " 不存在")
  51. } else {
  52. err = errors.New("获取指标失败:Err:" + tmpErr.Error())
  53. }
  54. errMsg = "数据计算失败"
  55. return
  56. }
  57. edbInfoList = append(edbInfoList, fromEdbInfo)
  58. }
  59. for _, v := range formulaSlice {
  60. formulaMap, e := utils.CheckFormula(v)
  61. if e != nil {
  62. err = fmt.Errorf("公式错误,请重新填写")
  63. return
  64. }
  65. ok, _ := models.CheckFormula2(edbInfoList, formulaMap, v, edbInfoIdBytes)
  66. if !ok {
  67. errMsg = "生成计算指标失败,请使用正确的计算公式"
  68. err = errors.New(errMsg)
  69. return
  70. }
  71. }
  72. return
  73. }
  74. func CalculateByRuleByNine(formulaStr string, edbInfoList []*models.EdbInfo, edbInfoIdBytes []string, emptyType, maxEmptyType int) (dataList []*models.EdbDataList, err error) {
  75. realSaveDataMap := make(map[string]map[int]float64)
  76. saveDataMap := make(map[string]map[int]float64)
  77. dateList := make([]string, 0) //日期
  78. var minLatestDate, maxStartDate time.Time
  79. formulaStr = strings.ToUpper(formulaStr)
  80. for edbInfoIndex, v := range edbInfoList {
  81. sourceDataList, tmpErr := models.GetPredictEdbDataListAll(v, 1)
  82. if tmpErr != nil {
  83. err = tmpErr
  84. return
  85. }
  86. dataMap := make(map[string]float64)
  87. for _, dv := range sourceDataList {
  88. if val, ok := realSaveDataMap[dv.DataTime]; ok {
  89. if _, ok1 := val[v.EdbInfoId]; !ok1 {
  90. val[v.EdbInfoId] = dv.Value
  91. }
  92. } else {
  93. temp := make(map[int]float64)
  94. temp[v.EdbInfoId] = dv.Value
  95. realSaveDataMap[dv.DataTime] = temp
  96. }
  97. if val, ok := saveDataMap[dv.DataTime]; ok {
  98. if _, ok1 := val[v.EdbInfoId]; !ok1 {
  99. val[v.EdbInfoId] = dv.Value
  100. }
  101. } else {
  102. temp2 := make(map[int]float64)
  103. temp2[v.EdbInfoId] = dv.Value
  104. saveDataMap[dv.DataTime] = temp2
  105. }
  106. if edbInfoIndex == 0 {
  107. dateList = append(dateList, dv.DataTime)
  108. tmpDate, _ := time.ParseInLocation(utils.FormatDate, dv.DataTime, time.Local)
  109. if minLatestDate.IsZero() || tmpDate.After(minLatestDate) {
  110. minLatestDate = tmpDate
  111. }
  112. if maxStartDate.IsZero() || tmpDate.Before(maxStartDate) {
  113. maxStartDate = tmpDate
  114. }
  115. }
  116. }
  117. item := new(models.CalculateItems)
  118. item.EdbInfoId = v.EdbInfoId
  119. item.DataMap = dataMap
  120. }
  121. models.HandleDateSaveDataMap(dateList, maxStartDate, minLatestDate, realSaveDataMap, saveDataMap, edbInfoList, emptyType)
  122. dataList = make([]*models.EdbDataList, 0)
  123. formulaDateSlice, formulaDateMap, err := utils.HandleFormulaJson(formulaStr, minLatestDate)
  124. if err != nil {
  125. return
  126. }
  127. existDataMap := make(map[string]string)
  128. maxDealFlag := false
  129. if emptyType == 4 && maxEmptyType == 2 {
  130. maxDealFlag = true
  131. }
  132. for k, date := range dateList {
  133. sv := saveDataMap[date]
  134. if emptyType == 1 {
  135. if len(sv) != len(edbInfoList) {
  136. continue
  137. }
  138. }
  139. formulaMap := make(map[string]string)
  140. formulaStr = ""
  141. for _, fv := range formulaDateSlice {
  142. if date < fv {
  143. if f, ok := formulaDateMap[fv]; ok {
  144. formulaStr = f
  145. formulaMap, err = utils.CheckFormula(formulaStr)
  146. if err != nil {
  147. err = fmt.Errorf("公式错误,请重新填写")
  148. return
  149. }
  150. }
  151. break
  152. }
  153. }
  154. if formulaStr == "" {
  155. continue
  156. }
  157. svMax := make(map[int]float64)
  158. if maxDealFlag {
  159. if svMaxData, ok := realSaveDataMap[date]; ok {
  160. svMax = svMaxData
  161. }
  162. }
  163. formulaFormStr := models.ReplaceFormula(edbInfoList, sv, svMax, formulaMap, formulaStr, edbInfoIdBytes, maxDealFlag)
  164. if formulaFormStr == `` {
  165. continue
  166. }
  167. fmt.Println(fmt.Sprintf("%s:formulaFormStr:%s", date, formulaFormStr))
  168. calVal, err := engine.ParseAndExec(formulaFormStr)
  169. if err != nil {
  170. err = errors.New("计算失败:获取计算值失败 Err:" + err.Error() + ";formulaStr:" + formulaFormStr)
  171. fmt.Println(err)
  172. return nil, err
  173. }
  174. saveValue, _ := decimal.NewFromFloat(calVal).Round(4).Float64() //utils.SubFloatToString(calVal, 4)
  175. dataTime, _ := time.Parse(utils.FormatDate, date)
  176. timestamp := dataTime.UnixNano() / 1e6
  177. if _, existOk := existDataMap[date]; !existOk {
  178. tmpPredictEdbRuleData := &models.EdbDataList{
  179. EdbDataId: k,
  180. EdbInfoId: 0,
  181. DataTime: date,
  182. DataTimestamp: timestamp,
  183. Value: saveValue,
  184. }
  185. dataList = append(dataList, tmpPredictEdbRuleData)
  186. }
  187. existDataMap[date] = date
  188. }
  189. return
  190. }