// Check the input for custom delimiters, and return the remaining string public static string checkForAndSetCustomDelimiters(string input, ChallengeCalculatorOptions options) { // delimiter specifier has format //{delimiter}\n for a // single char and //[{delimiter}]\n for a multi char delimiter if (input.Substring(0, 2) != "//") { return(input); } if (input[2] == '[') // multi char delimiter { var indexOfFirstNewLine = input.IndexOf('\n'); // find the delimiters at these char indexes // //[delimiter1][delimiter2]\n // 012.......................^ = first newline var delimiterString = input.Substring(2, indexOfFirstNewLine - 2); options.delimiters.AddRange(Regex.Matches(delimiterString, "(?<=\\[).+?(?=\\])").Cast <Match>().Select(m => m.Value).ToList()); // return without the first for chars that specify the delimiter return(input.Substring(indexOfFirstNewLine + 1, input.Length - indexOfFirstNewLine - 1)); } else // single char delimiter // find the delimiter at this char index // //x\n // 0123 { options.delimiters.Add($"{input[2]}"); return(input.Substring(4, input.Length - 4)); } }
public static void Main(string[] args) { var options = new ChallengeCalculatorOptions(args); // process custom delimiters on first run var userInput = collectUserInput(); var processedInput = checkForAndSetCustomDelimiters(userInput, options); var result = sumString(processedInput, options); Console.WriteLine($"{result.formula} = {result.sum}"); // run once option (used in unit tests) if (options.runOnce == true) { return; } while (true) { // do no process custom delimiters on subsequent runs userInput = collectUserInput(); result = sumString(processedInput, options); Console.WriteLine($"{result.formula} = {result.sum}"); } }
public static CalculatorResult sumString(string input, ChallengeCalculatorOptions options) { var split = splitInput(input, options); // maintain a list of encountered negative numbers for the // exception message var negatives = new List <int>(); int sum = 0; var formulaStringBuilder = new StringBuilder(); foreach (var segment in split) { var integer = interpretAsValidInteger(segment, options); sum += integer; formulaStringBuilder.Append(integer); formulaStringBuilder.Append("+"); if (integer < 0 && !options.allowNegative) { negatives.Add(integer); } } if (negatives.Count > 0) { throw new ArgumentException($"Found these negatives: {String.Join(", ", negatives)}"); } // shave off the last '+' formulaStringBuilder.Remove(formulaStringBuilder.Length - 1, 1); return(new CalculatorResult(sum, formulaStringBuilder.ToString())); }
// interpret the string as an int less then or equal to 1000, // or return 0 on a failure. static int interpretAsValidInteger(string s, ChallengeCalculatorOptions options) { if (!int.TryParse(s.Trim(), out int n)) { return(0); } return(n > options.upperBound ? 0 : n); }
// split an input line into substrings static string[] splitInput(string line, ChallengeCalculatorOptions options) { return(line.Split(options.delimiters.ToArray(), StringSplitOptions.None)); }