Loading android/util.go +39 −5 Original line number Diff line number Diff line Loading @@ -65,21 +65,55 @@ func JoinWithSuffix(strs []string, suffix string, separator string) string { return buf.String() } // SorterStringKeys returns the keys of the given string-keyed map in the ascending order // SorterStringKeys returns the keys of the given string-keyed map in the ascending order. func SortedStringKeys(m interface{}) []string { v := reflect.ValueOf(m) if v.Kind() != reflect.Map { panic(fmt.Sprintf("%#v is not a map", m)) } keys := v.MapKeys() s := make([]string, 0, len(keys)) for _, key := range keys { s = append(s, key.String()) if v.Len() == 0 { return nil } iter := v.MapRange() s := make([]string, 0, v.Len()) for iter.Next() { s = append(s, iter.Key().String()) } sort.Strings(s) return s } // stringValues returns the values of the given string-valued map in randomized map order. func stringValues(m interface{}) []string { v := reflect.ValueOf(m) if v.Kind() != reflect.Map { panic(fmt.Sprintf("%#v is not a map", m)) } if v.Len() == 0 { return nil } iter := v.MapRange() s := make([]string, 0, v.Len()) for iter.Next() { s = append(s, iter.Value().String()) } return s } // SortedStringValues returns the values of the given string-valued map in the ascending order. func SortedStringValues(m interface{}) []string { s := stringValues(m) sort.Strings(s) return s } // SortedUniqueStringValues returns the values of the given string-valued map in the ascending order // with duplicates removed. func SortedUniqueStringValues(m interface{}) []string { s := stringValues(m) return SortedUniqueStrings(s) } // IndexList returns the index of the first occurrence of the given string in the list or -1 func IndexList(s string, list []string) int { for i, l := range list { Loading android/util_test.go +114 −0 Original line number Diff line number Diff line Loading @@ -640,3 +640,117 @@ func BenchmarkFirstUniqueStrings(b *testing.B) { }) } } func TestSortedStringKeys(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"a": "foo", "b": "bar"}, expected: []string{"a", "b"}, }, { name: "interface values", in: map[string]interface{}{"a": nil, "b": nil}, expected: []string{"a", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedStringKeys(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } } func TestSortedStringValues(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"foo": "a", "bar": "b"}, expected: []string{"a", "b"}, }, { name: "duplicates", in: map[string]string{"foo": "a", "bar": "b", "baz": "b"}, expected: []string{"a", "b", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedStringValues(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } } func TestSortedUniqueStringValues(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"foo": "a", "bar": "b"}, expected: []string{"a", "b"}, }, { name: "duplicates", in: map[string]string{"foo": "a", "bar": "b", "baz": "b"}, expected: []string{"a", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedUniqueStringValues(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } } Loading
android/util.go +39 −5 Original line number Diff line number Diff line Loading @@ -65,21 +65,55 @@ func JoinWithSuffix(strs []string, suffix string, separator string) string { return buf.String() } // SorterStringKeys returns the keys of the given string-keyed map in the ascending order // SorterStringKeys returns the keys of the given string-keyed map in the ascending order. func SortedStringKeys(m interface{}) []string { v := reflect.ValueOf(m) if v.Kind() != reflect.Map { panic(fmt.Sprintf("%#v is not a map", m)) } keys := v.MapKeys() s := make([]string, 0, len(keys)) for _, key := range keys { s = append(s, key.String()) if v.Len() == 0 { return nil } iter := v.MapRange() s := make([]string, 0, v.Len()) for iter.Next() { s = append(s, iter.Key().String()) } sort.Strings(s) return s } // stringValues returns the values of the given string-valued map in randomized map order. func stringValues(m interface{}) []string { v := reflect.ValueOf(m) if v.Kind() != reflect.Map { panic(fmt.Sprintf("%#v is not a map", m)) } if v.Len() == 0 { return nil } iter := v.MapRange() s := make([]string, 0, v.Len()) for iter.Next() { s = append(s, iter.Value().String()) } return s } // SortedStringValues returns the values of the given string-valued map in the ascending order. func SortedStringValues(m interface{}) []string { s := stringValues(m) sort.Strings(s) return s } // SortedUniqueStringValues returns the values of the given string-valued map in the ascending order // with duplicates removed. func SortedUniqueStringValues(m interface{}) []string { s := stringValues(m) return SortedUniqueStrings(s) } // IndexList returns the index of the first occurrence of the given string in the list or -1 func IndexList(s string, list []string) int { for i, l := range list { Loading
android/util_test.go +114 −0 Original line number Diff line number Diff line Loading @@ -640,3 +640,117 @@ func BenchmarkFirstUniqueStrings(b *testing.B) { }) } } func TestSortedStringKeys(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"a": "foo", "b": "bar"}, expected: []string{"a", "b"}, }, { name: "interface values", in: map[string]interface{}{"a": nil, "b": nil}, expected: []string{"a", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedStringKeys(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } } func TestSortedStringValues(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"foo": "a", "bar": "b"}, expected: []string{"a", "b"}, }, { name: "duplicates", in: map[string]string{"foo": "a", "bar": "b", "baz": "b"}, expected: []string{"a", "b", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedStringValues(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } } func TestSortedUniqueStringValues(t *testing.T) { testCases := []struct { name string in interface{} expected []string }{ { name: "nil", in: map[string]string(nil), expected: nil, }, { name: "empty", in: map[string]string{}, expected: nil, }, { name: "simple", in: map[string]string{"foo": "a", "bar": "b"}, expected: []string{"a", "b"}, }, { name: "duplicates", in: map[string]string{"foo": "a", "bar": "b", "baz": "b"}, expected: []string{"a", "b"}, }, } for _, tt := range testCases { t.Run(tt.name, func(t *testing.T) { got := SortedUniqueStringValues(tt.in) if g, w := got, tt.expected; !reflect.DeepEqual(g, w) { t.Errorf("wanted %q, got %q", w, g) } }) } }