The two below solutions are similiar to 41. First Missing Positive with some modification.
Since the values range 1...n, we can add all elements to set, and iterate 1...n to find the missing number.
def findDisappearedNumbers(self, nums: List[int]) -> List[int]:
n = len(nums)
nums_set = set(nums)
missing = []
for i in range(1, n + 1):
if i not in nums_set:
missing.append(i)
return missing- Time Complexity:
O(n). - Space Complexity:
O(n).
Since the values range 1...n, we can use index to represent the number we saw before. For example, nums[i] is 4, then we mark index 3 as seen (negative).
We iterate all elements, we mark abs(nums[nums[i] - 1]) as negative (we use 0 indexed, so we have to minus one, get absolute value because it might has been marked before) to indicate that we have seen nums[i].
Then iterate again to find the index of positive number (not be marked, not seen before)
Index: 0 1 2 3
Input: [4, 3, 3, 4]
i
4, 3, 3,-4 // Marked index 4 - 1 = 3 as negative
i
4, 3,-3,-4 // Marked index 3 - 1 = 2 as negative
iThe input array becomes [4, 3, -3, -4], and we find out nums[0] and nums[1] are positive (not marked, not seen before), so return [0, 1].
def findDisappearedNumbers(self, nums: List[int]) -> List[int]:
# See 3, mark A[2] as negative
for i in range(len(nums)):
value = abs(nums[i]) - 1
nums[value] = -abs(nums[value])
missing = []
for i in range(len(nums)):
if nums[i] > 0:
missing.append(i + 1)
return missingfun findDisappearedNumbers(nums: IntArray): List<Int> {
val disappearedNumbers = mutableListOf<Int>()
for (i in 0 until nums.size) {
val index = nums[i].abs() - 1
nums[index] = -nums[index].abs()
}
for (i in 0 until nums.size) {
if (nums[i] > 0) {
disappearedNumbers.add(i + 1)
}
}
return disappearedNumbers
}
- Time Complexity:
O(n)for only two for-loops. - Space Complexity:
O(1)no extra space.
See My Notes
We can use array itself as hash table and index as key since the value range in 1..n, we can place the value at the index it should be, that is nums[i] - 1 = i. For example, A[0] = 4, then we should move to A[3] by swapping.
Then iterate again to find the value that is not at the right index (the value != index), then it would be the missing number.
def findDisappearedNumbers(self, nums: List[int]) -> List[int]:
def swap(arr, i, j):
arr[i], arr[j] = arr[j], arr[i]
# See 3, place to A[2] by swapping
n = len(nums)
for i in range(n):
while 0 < nums[i] <= n and nums[i] != nums[nums[i] - 1]:
swap(nums, i, nums[i] - 1)
missing = []
for i in range(n):
if nums[i] != i + 1:
missing.append(i + 1)
return missingfun findDisappearedNumbers(nums: IntArray): List<Int> {
val n = nums.size
var i = 0
while (i < nums.size) {
val value = nums[i]
if (nums[value - 1] != value) nums.swap(i, value - 1)
else i++
}
val results = mutableListOf<Int>()
for (i in 0 until n) {
if (nums[i] != i + 1) results.add(i + 1)
}
return results
}
private fun IntArray.swap(i: Int, j: Int) {
val temp = this[i]
this[i] = this[j]
this[j] = temp
}