Repository: vaskoz/dailycodingproblem-go (go)

Issue:
Day 163
Good morning! Here's your coding interview problem for today.

This problem was asked by Jane Street.

Given an arithmetic expression in Reverse Polish Notation, write a program to evaluate it.

The expression is given as a list of numbers and operands. For example: `[5, 3, '+']` should return `5 + 3 = 8`.

For example, `[15, 7, 1, 1, '+', '-', '/', 3, '*', 2, 1, 1, '+', '+', '-']` should return `5`, since it is equivalent to `((15 / (7 - (1 + 1))) * 3) - (2 + (1 + 1)) = 5`.

You can assume the given expression is always valid.

Pull request:
Day163
Resolves #336.

Patch:
diff --git a/README.md b/README.md
index f78f0dc..9e5c104 100644
--- a/README.md
+++ b/README.md
@@ -170,3 +170,4 @@ problems from
 * [Day 157](https://github.com/vaskoz/dailycodingproblem-go/issues/327)
 * [Day 158](https://github.com/vaskoz/dailycodingproblem-go/issues/329)
 * [Day 159](https://github.com/vaskoz/dailycodingproblem-go/issues/331)
+* [Day 163](https://github.com/vaskoz/dailycodingproblem-go/issues/336)
diff --git a/day163/problem.go b/day163/problem.go
new file mode 100644
index 0000000..3593bc1
--- /dev/null
+++ b/day163/problem.go
@@ -0,0 +1,34 @@
+package day163
+
+import "strconv"
+
+// ReversePolishCalculator calculates the result of the expression
+// given in reverse polish notation.
+// It assumes the given expression is always valid.
+// Bad input causes a panic.
+func ReversePolishCalculator(input []string) int {
+	var stack []int
+	for _, v := range input {
+		switch v {
+		case "+":
+			r := stack[len(stack)-2] + stack[len(stack)-1]
+			stack = append(stack[:len(stack)-2], r)
+		case "-":
+			r := stack[len(stack)-2] - stack[len(stack)-1]
+			stack = append(stack[:len(stack)-2], r)
+		case "*":
+			r := stack[len(stack)-2] * stack[len(stack)-1]
+			stack = append(stack[:len(stack)-2], r)
+		case "/":
+			r := stack[len(stack)-2] / stack[len(stack)-1]
+			stack = append(stack[:len(stack)-2], r)
+		default:
+			i, err := strconv.Atoi(v)
+			if err != nil {
+				panic("invalid input")
+			}
+			stack = append(stack, i)
+		}
+	}
+	return stack[0]
+}


Test patch:
diff --git a/day163/problem_test.go b/day163/problem_test.go
new file mode 100644
index 0000000..6c4c7f7
--- /dev/null
+++ b/day163/problem_test.go
@@ -0,0 +1,38 @@
+package day163
+
+import "testing"
+
+var testcases = []struct {
+	input    []string
+	expected int
+}{
+	{[]string{"5", "3", "+"}, 8},
+	{[]string{"15", "7", "1", "1", "+", "-", "/", "3", "*", "2", "1", "1", "+", "+", "-"}, 5},
+}
+
+func TestReversePolishCalculator(t *testing.T) {
+	t.Parallel()
+	for _, tc := range testcases {
+		if result := ReversePolishCalculator(tc.input); result != tc.expected {
+			t.Errorf("Expected %v got %v", tc.expected, result)
+		}
+	}
+}
+
+func TestReversePolishCalculatorBadInput(t *testing.T) {
+	t.Parallel()
+	defer func() {
+		if r := recover(); r == nil {
+			t.Errorf("Expect a panic for bad input")
+		}
+	}()
+	ReversePolishCalculator([]string{"15", "20", "abc", "?"})
+}
+
+func BenchmarkReversePolishCalculator(b *testing.B) {
+	for i := 0; i < b.N; i++ {
+		for _, tc := range testcases {
+			ReversePolishCalculator(tc.input)
+		}
+	}
+}