108 lines
3.4 KiB
C#
108 lines
3.4 KiB
C#
|
|
using System.Globalization;
|
||
|
|
using DiunaBIWebAPI.dataProcessors;
|
||
|
|
using WebAPI.Models;
|
||
|
|
using AngouriMath;
|
||
|
|
using AngouriMath.Extensions;
|
||
|
|
|
||
|
|
namespace WebAPI.Calculator
|
||
|
|
{
|
||
|
|
public class BaseCalc
|
||
|
|
{
|
||
|
|
public string Expresion { get; set; }
|
||
|
|
|
||
|
|
private string ResultCode { get; set; }
|
||
|
|
private string Formula { get; set; }
|
||
|
|
|
||
|
|
public BaseCalc(string expresion)
|
||
|
|
{
|
||
|
|
Expresion = expresion;
|
||
|
|
Formula = Expresion.Split("=")[1];
|
||
|
|
ResultCode = Expresion.Split("=")[0];
|
||
|
|
}
|
||
|
|
|
||
|
|
public bool IsFormulaCorrect()
|
||
|
|
{
|
||
|
|
// check left side of expression
|
||
|
|
if (!ResultCode.StartsWith("[") || !ResultCode.EndsWith("]"))
|
||
|
|
{
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
if (!ResultCode.Substring(1, ResultCode.Length - 2).All(char.IsDigit))
|
||
|
|
{
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
|
||
|
|
ResultCode = ResultCode.Substring(1, ResultCode.Length - 2);
|
||
|
|
|
||
|
|
// check right side of expression
|
||
|
|
if (!(!string.IsNullOrEmpty(Formula) &&
|
||
|
|
Formula.All(c => char.IsDigit(c) || c == '[' || c == ']' || c == '+')))
|
||
|
|
{
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
|
||
|
|
return true;
|
||
|
|
}
|
||
|
|
|
||
|
|
public Record CalculateT3(List<Record> records)
|
||
|
|
{
|
||
|
|
Record result = new Record
|
||
|
|
{
|
||
|
|
Id = Guid.NewGuid(),
|
||
|
|
Code = this.ResultCode,
|
||
|
|
CreatedAt = DateTime.UtcNow,
|
||
|
|
ModifiedAt = DateTime.UtcNow,
|
||
|
|
};
|
||
|
|
List<string> codes = GetCodes();
|
||
|
|
List<Record> ingredients = new List<Record>();
|
||
|
|
foreach (string code in codes)
|
||
|
|
{
|
||
|
|
Record? ingredient = records.FirstOrDefault(r => r.Code == code);
|
||
|
|
if (ingredient == null)
|
||
|
|
{
|
||
|
|
throw new Exception($"Record for code {code} not found.");
|
||
|
|
}
|
||
|
|
ingredients.Add(ingredient);
|
||
|
|
}
|
||
|
|
|
||
|
|
for (int i = 1; i <= 32; i++)
|
||
|
|
{
|
||
|
|
string formula = Formula;
|
||
|
|
foreach (Record ingredient in ingredients)
|
||
|
|
{
|
||
|
|
formula = formula.Replace($"[{ingredient.Code}]", ProcessHelper.getValue(ingredient, i)?.ToString(CultureInfo.InvariantCulture));
|
||
|
|
}
|
||
|
|
if (formula.Contains("["))
|
||
|
|
{
|
||
|
|
throw new Exception($"Not all placeholders were replaced. Value{i} [{formula}]");
|
||
|
|
}
|
||
|
|
|
||
|
|
Entity expr = formula;
|
||
|
|
double val = (double)expr.EvalNumerical();
|
||
|
|
ProcessHelper.setValue(result, i, (double)expr.EvalNumerical());
|
||
|
|
}
|
||
|
|
return result;
|
||
|
|
}
|
||
|
|
|
||
|
|
private List<string> GetCodes()
|
||
|
|
{
|
||
|
|
List<string> codes = new List<string>();
|
||
|
|
int endIndex = -1;
|
||
|
|
|
||
|
|
while (true)
|
||
|
|
{
|
||
|
|
int startIndex = Formula.IndexOf("[", endIndex + 1, StringComparison.CurrentCulture);
|
||
|
|
endIndex = Formula.IndexOf("]", startIndex + 1, StringComparison.CurrentCulture);
|
||
|
|
|
||
|
|
if (startIndex == -1 || endIndex == -1)
|
||
|
|
{
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
string valueCode = Formula.Substring(startIndex + 1, endIndex - startIndex - 1);
|
||
|
|
codes.Add(valueCode);
|
||
|
|
}
|
||
|
|
return codes;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|