1、排序
在对数字从小到大排序之后,数组的重复元素一定出现在相邻位置中
func containsDuplicate(nums []int) bool {
sort.Ints(nums)
for i := 1; i < len(nums); i++ {
if nums[i] == nums[i-1] {
return true
}
}
return false
}
复杂度分析
时间复杂度:O(NlogN),其中 N 为数组的长度。需要对数组进行排序。
空间复杂度:O(logN),其中 N 为数组的长度。注意我们在这里应当考虑递归调用栈的深度。
2、哈希表
对于数组中每个元素,我们将它插入到哈希表中。如果插入一个元素时发现该元素已经存在于哈希表中,则说明存在重复的元素。
func containsDuplicate(nums []int) bool {
set := map[int]struct{}{}
for _, v := range nums {
if _, has := set[v]; has {
return true
}
set[v] = struct{}{}
}
return false
}
复杂度分析
-
时间复杂度:O(N)O(N),其中 NN 为数组的长度。
-
空间复杂度:O(N)O(N),其中 NN 为数组的长度。
3、原地交换
func findRepeatNumber(nums []int) int {
i := 0
for i < len(nums) {
if nums[i] == i {
i++
continue
}
if nums[nums[i]] == nums[i] {
return nums[i]
}
nums[nums[i]], nums[i] = nums[i], nums[nums[i]]
}
return -1
}
复杂度分析
97%
时间复杂度 O(N) : 遍历数组使用 O(N),每轮遍历的判断和交换操作使用 O(1)
32%
空间复杂度 O(1): 使用常数复杂度的额外空间
4、
func findRepeatNumber(nums []int) int {
length := len(nums)
ysSlice := make([]int,length)
for i:=0;i<length;i++ {
ysSlice[nums[i]]++
if ysSlice[nums[i]] >1 {
return nums[i]
}
}
return -1
}
时间97%
空间98%