package main import ( "fmt" "testing" ) func TestParse(t *testing.T) { cases := []string{ "[1,2]", "[[3,2],1]", "[[3,2],[4,5]]", "[[3,2],[[7,8],5]]", "[[1,2],3]", "[9,[8,7]]", "[[1,9],[8,5]]", "[[[[1,2],[3,4]],[[5,6],[7,8]]],9]", "[[[9,[3,8]],[[0,9],6]],[[[3,7],[4,9]],3]]", "[[[[1,3],[5,3]],[[1,3],[8,7]]],[[[4,9],[6,9]],[[8,2],[7,3]]]]", } for _, input := range cases { p := Parse(input) if input != p.String() { t.Log(p.String()) t.Fail() } } } func TestMustExplode(t *testing.T) { cases := map[string]bool{ "[1,2]": false, "[[[[2,4],4],[2,3]],1]": false, "[[[[[4,3],4],4],1],3]": true, "[2,[1,[4,[3,[4,3]]]]]": true, "[[[[0,7],4],[7,[[8,4],9]]],[1,1]]": true, } for input, output := range cases { if MustExplode(0, Parse(input)) != output { t.Log(input) t.Fail() } } } func TestSplit(t *testing.T) { cases := map[*pair]string{ {left: 1, right: 1}: "[1,1]", {left: 10, right: 1}: "[[5,5],1]", {left: 11, right: 1}: "[[5,6],1]", {left: 12, right: 1}: "[[6,6],1]", {left: 12, right: 12}: "[[6,6],12]", {left: 2, right: 12}: "[2,[6,6]]", { leftp: &pair{left: 15, right: 9}, rightp: &pair{left: 8, right: 1}, }: "[[[7,8],9],[8,1]]", { leftp: &pair{left: 1, right: 9}, rightp: &pair{left: 8, right: 15}, }: "[[1,9],[8,[7,8]]]", } for input, expected := range cases { Split(input) if input.String() != expected { t.Log(input.String(), expected) t.Fail() } } } func TestMustSplit(t *testing.T) { cases := map[*pair]bool{ {left: 1, right: 1}: false, {left: 10, right: 1}: true, {left: 11, right: 1}: true, {left: 12, right: 1}: true, {left: 12, right: 12}: true, {left: 2, right: 12}: true, { leftp: &pair{left: 1, right: 9}, rightp: &pair{left: 8, right: 5}, }: false, { leftp: &pair{left: 1, right: 9}, rightp: &pair{left: 8, right: 15}, }: true, } for input, output := range cases { result := MustSplit(input) if result != output { t.Log(input.String()) t.Fail() } } } func TestAdd(t *testing.T) { cases := map[string][]*pair{ "[[1,2],[[3,4],5]]": { &pair{left: 1, right: 2}, &pair{leftp: &pair{left: 3, right: 4}, right: 5}, }, } for answer, pairs := range cases { r := Add(pairs[0], pairs[1]) if r.String() != answer { fmt.Printf("%s %s", r, answer) t.Fail() } } } func TestReduce(t *testing.T) { cases := map[*pair]string{ {left: 1, right: 1}: "[1,1]", {left: 10, right: 1}: "[[5,5],1]", {left: 11, right: 1}: "[[5,6],1]", {left: 12, right: 1}: "[[6,6],1]", {left: 12, right: 13}: "[[6,6],[6,7]]", {left: 2, right: 12}: "[2,[6,6]]", { leftp: &pair{left: 15, right: 9}, rightp: &pair{left: 8, right: 1}, }: "[[[7,8],9],[8,1]]", { leftp: &pair{left: 1, right: 9}, rightp: &pair{left: 8, right: 15}, }: "[[1,9],[8,[7,8]]]", } for input, expected := range cases { Reduce(input) if input.String() != expected { t.Log(input.String(), expected) t.Fail() } } } func TestMagnitude(t *testing.T) { cases := map[int]*pair{ 29: {left: 9, right: 1}, 21: {left: 1, right: 9}, 129: { leftp: &pair{left: 9, right: 1}, rightp: &pair{left: 1, right: 9}, }, 143: { leftp: &pair{left: 1, right: 2}, rightp: &pair{leftp: &pair{left: 3, right: 4}, right: 5}, }, } for answer, pair := range cases { r := pair.Magnitude() if r != answer { fmt.Printf("%d %d", r, answer) t.Fail() } } }