material_calc.js 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768
  1. 'use strict';
  2. /**
  3. *
  4. *
  5. * @author Mai
  6. * @date
  7. * @version
  8. */
  9. const math = require('mathjs');
  10. class MaterialCalculate {
  11. constructor(ctx, stage_id_list, tenderInfo) {
  12. this.ctx = ctx;
  13. this.stageList = stage_id_list;
  14. this.percentReg = /[0-9]+%/g;
  15. this.tenderInfo = tenderInfo;
  16. }
  17. /**
  18. * 获取 计算基数
  19. * @returns {Promise<void>}
  20. */
  21. async getCalcBase() {
  22. if (this.bases) { return; }
  23. const stage_list = await this.ctx.service.stage.getStageMsgByStageId(this.stageList);
  24. const bases = await this.ctx.service.stage.getMaterialCalcBase(stage_list, this.tenderInfo);
  25. this.bases = bases.sort(function(a, b) {
  26. return a.sort - b.sort;
  27. // if (a && b) {
  28. // return b.code.indexOf(a.code) >= 0 ? 1 : 0;
  29. // } else {
  30. // return 0;
  31. // }
  32. });
  33. for (const b of this.bases) {
  34. b.reg = new RegExp(b.code, 'igm');
  35. }
  36. }
  37. _calculateExpr(expr) {
  38. try {
  39. let formula = expr;
  40. for (const b of this.bases) {
  41. formula = formula.replace(b.reg, b.value);
  42. }
  43. const percent = formula.match(this.percentReg);
  44. if (percent) {
  45. for (const p of percent) {
  46. const v = math.eval(p.replace('%', '/100'));
  47. formula = formula.replace(p, v);
  48. }
  49. }
  50. const value = parseFloat(math.eval(formula));
  51. return value;
  52. } catch (err) {
  53. return 0;
  54. }
  55. }
  56. async calculateExpr(expr) {
  57. await this.getCalcBase();
  58. return this._calculateExpr(expr);
  59. }
  60. }
  61. module.exports = MaterialCalculate;