public void TestProcessorComplex(string[] postfix, int result) { var request = new CalculatePostfixRequest() { CalculateStack = postfix.ToList(), Operators = new OperatorList().Operators }; BResult <CalculatePostfixResponse> br = new CalculatePostfixProcessor().Calculate(request); Assert.Empty(br.Error); Assert.Equal(result, br.Result.CalculatedValue); }
/// <summary> /// Calculate output of postfix expression /// </summary> /// <param name="inputValue"></param> /// <returns></returns> public BResult <CalculatePostfixResponse> Calculate(CalculatePostfixRequest inputValue) { var result = new BResult <CalculatePostfixResponse>() { Result = new CalculatePostfixResponse() }; var stack = new Stack <string>(); IDictionary <string, Operator> operators = inputValue.Operators; IDictionary <string, Type> mathOperators = GetMathOperators(operators); foreach (string token in inputValue.CalculateStack) { var tType = TokenHelper.GetTokenType(token, operators); switch (tType) { case TokenType.NUMBER: stack.Push(token); break; case TokenType.OPERATOR: string rightOperand = stack.Pop(); string leftOperand = stack.Pop(); Type operatorType = mathOperators.Where(k => k.Key.Equals(token)).Select(v => v.Value).FirstOrDefault(); // Check for null operatorType var obj = Activator.CreateInstance(operatorType) as IMathOperator <CalculatePostfixResponse>; BResult <CalculatePostfixResponse> br = obj.MathOperator(leftOperand, rightOperand); result.Error.AddRange(br.Error); stack.Push(br.Result.CalculatedValue.ToString()); break; case TokenType.UNDEFINED: case TokenType.LEFTPARENTHESIS: case TokenType.RIGHTPARENTHESIS: case TokenType.EQUAL: case TokenType.WHITESPACE: default: result.Error.Add(new HError("Calculate", $"Unknown TokenType: {tType}")); break; } } result.Result.CalculatedValue = Convert.ToInt32(stack.Pop()); return(result); }
public async Task <BResult <CalculatorResponse> > ExecuteAsync(CalculatorRequest request) { BResult <CalculatorResponse> result = new BResult <CalculatorResponse> { Result = new CalculatorResponse() }; try { if (string.IsNullOrWhiteSpace(request.Input)) { result.Error.Add(new HError("Calculator", "Invalid request - null input")); } if (request.Input.Any(c => char.IsLetter(c))) { result.Error.Add(new HError("Calculator", "Invalid input - contains letters")); } if (!request.Input.EndsWith("=")) { result.Error.Add(new HError("Calculator", "Invalid input - Expression must end with '='")); } if (_operators == null || _operators.Count == 0) { result.Error.Add(new HError("Calculator", "Invalid operator creation")); return(result); } // Check input string against valid list of valid operators / digits List <char> goodChar = _operators.Keys.SelectMany(s => s.ToCharArray()).ToList(); goodChar.AddRange(new List <char> { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '=', '(', ')' }); if (request.Input.Except(goodChar).Any()) { string validChar = string.Join(", ", goodChar.Select(c => c.ToString()).ToArray()); result.Error.Add(new HError("Calculator", $"Invalid input - Valid inputs are: {validChar}")); } if (result.Error.Count > 0) { return(result); } var calculateInputRequest = new CalculateInfixRequest() { Input = request.Input, Operators = _operators }; BResult <CalculateInfixResponse> bResultInput = new InfixToPostfixProcessor().InfixToPostfix(calculateInputRequest); result.Error.AddRange(bResultInput.Error); //if (result.Error.Any()) // return result; var calulateOutputRequest = new CalculatePostfixRequest() { CalculateStack = bResultInput.Result.CalculateStack, Operators = _operators }; BResult <CalculatePostfixResponse> bResultOutput = new CalculatePostfixProcessor().Calculate(calulateOutputRequest); result.Error.AddRange(bResultOutput.Error); result.Result.Output = bResultOutput.Result.CalculatedValue; } catch (Exception ex) { result.Error.Add(new HException(_herrorRepository, "Calculator", "Exception will executing Calculator", ex)); } await Task.Delay(0); return(result); }