是否有类似于Go中的slice.contains(object)方法,而无需在slice中逐个搜索每个元素?
当前回答
如果切片已排序,则排序包中实现了二进制搜索。
其他回答
如果你有一个字节切片,你可以使用bytes包:
package main
import "bytes"
func contains(b []byte, sub byte) bool {
return bytes.Contains(b, []byte{sub})
}
func main() {
b := contains([]byte{10, 11, 12, 13, 14}, 13)
println(b)
}
或suffixarray包:
package main
import "index/suffixarray"
func contains(b []byte, sub byte) bool {
return suffixarray.New(b).Lookup([]byte{sub}, 1) != nil
}
func main() {
b := contains([]byte{10, 11, 12, 13, 14}, 13)
println(b)
}
如果你有一个int片,你可以使用intsets包:
package main
import "golang.org/x/tools/container/intsets"
func main() {
var s intsets.Sparse
for n := 10; n < 20; n++ {
s.Insert(n)
}
b := s.Has(16)
println(b)
}
https://golang.org/pkg/bytes https://golang.org/pkg/index/suffixarray https://pkg.go.dev/golang.org/x/tools/container/intsets
如果切片已排序,则排序包中实现了二进制搜索。
从Go 1.18开始,你可以使用slices包——特别是泛型Contains函数: https://pkg.go.dev/golang.org/x/exp/slices。
go get golang.org/x/exp/slices
import "golang.org/x/exp/slices"
things := []string{"foo", "bar", "baz"}
slices.Contains(things, "foo") // true
请注意,由于这是在标准库之外的一个实验包,所以它不绑定到Go 1兼容性承诺™,并且在正式添加到标准库之前可能会更改。
func Contain(target interface{}, list interface{}) (bool, int) {
if reflect.TypeOf(list).Kind() == reflect.Slice || reflect.TypeOf(list).Kind() == reflect.Array {
listvalue := reflect.ValueOf(list)
for i := 0; i < listvalue.Len(); i++ {
if target == listvalue.Index(i).Interface() {
return true, i
}
}
}
if reflect.TypeOf(target).Kind() == reflect.String && reflect.TypeOf(list).Kind() == reflect.String {
return strings.Contains(list.(string), target.(string)), strings.Index(list.(string), target.(string))
}
return false, -1
}
排序包提供构建块,如果你的片已经排序或你愿意排序。
input := []string{"bird", "apple", "ocean", "fork", "anchor"}
sort.Strings(input)
fmt.Println(contains(input, "apple")) // true
fmt.Println(contains(input, "grow")) // false
...
func contains(s []string, searchterm string) bool {
i := sort.SearchStrings(s, searchterm)
return i < len(s) && s[i] == searchterm
}
SearchString承诺,如果x不存在,将返回插入x的索引(它可以是len(a)),因此检查它可以揭示字符串是否包含已排序的切片。