是否有方法检查切片/Map是否存在值?
我想将一个值添加到切片中仅如果它不*存在于切片中。
这是可行的,但似乎冗长。有更好的方法来做到这一点吗?
orgSlice := []int{1, 2, 3}
newSlice := []int{}
newInt := 2
newSlice = append(newSlice, newInt)
for _, v := range orgSlice {
if v != newInt {
newSlice = append(newSlice, v)
}
}
newSlice == [2 1 3]
5条答案
按热度按时间8i9zcol21#
你的方法每次插入都需要线性时间,更好的方法是使用
map[int]struct{}
,或者,你也可以使用map[int]bool
或类似的函数,但是空的struct{}
有一个优点,它不占用任何额外的空间,因此map[int]struct{}
是整数集的常用选择。示例:
8gsdolmq2#
最有效的方法可能是遍历切片,如果找不到切片就追加。
它简单明了,对于小列表来说速度很快。
而且,它总是比当前基于Map的解决方案更快,无论如何,基于Map的解决方案都会在整个切片上迭代;这个解决方案在发现新值已经存在时立即返回。2两个解决方案都在迭代时比较元素。3(每个map赋值语句肯定在内部至少做一个map键比较。4)只有当你能在多次插入中维护它时,map才有用。5如果你在每次插入时都重建它,那么所有的优点都失去了。
如果您确实需要有效地处理大型列表,请考虑按排序顺序维护列表。(我怀疑排序顺序对您来说并不重要,因为您的第一个解决方案附加在列表的开头,而您的最新解决方案附加在末尾。)如果您始终保持列表排序,则可以使用sort.search函数来执行有效的二进制插入。
ndasle7k3#
另一种选择:
https://pkg.go.dev/golang.org/x/tools/container/intsets
3duebb1j4#
如果缺失数字的数目未知,则使用此选项
e5njpo685#
区分结构体的数组:
这里的结构体类似于:
对象将通过此处选中的字段区分: