diff --git a/problem31.py b/problem31.py new file mode 100644 index 00000000..f2612025 --- /dev/null +++ b/problem31.py @@ -0,0 +1,75 @@ +#sorting + linear search + +from typing import List + +class Solution: + def findDisappearedNumbers(self, nums: List[int]) -> List[int]: + #brute force will be O(n2) + #sorting + linear search + nums.sort() + result = [] + i = 0 + + for expected in range(1, len(nums)+1): + if i == len(nums) or nums[i] > expected: #to handle cases like [1,1] + result.append(expected) + while i < len(nums) and nums[i] == expected: #loop till next unqiue element + i += 1 + + return result + #nums[i] won't be less than expected because we are sorting it and the no.are in the range from 1 to n. where n is length of nums. + +# Time Complexity: O(nlogn + n) = O(nlogn) +# Space complexity: O(1) + +#Treating the array as a hashset + +class Solution: + def findDisappearedNumbers(self, nums: List[int]) -> List[int]: + #using the array as set itself + + result = [] + + for i in range(len(nums)): + idx = abs(nums[i])-1 #the no.s actual index in the array from 1 to N, 4 will be 3 + #1 will be 0 and so on. + if nums[idx] > 0: + nums[idx] *= -1 #mark the number at that idx negative + + for i in range(len(nums)): + if nums[i] > 0: + result.append(i+1) + + return result + +# Time Complexity: O(N) +# Space Complexity: O(1) + +#if negative numbers are involved example: +# [0,-1,3,-2,4,-2,-1,-3] +# range -3 to 4 = 4-(-3)+1 = 8 +# offset everything by range/2 = 4 +#this only works when the range is equal to the length of the array. + +class Solution: + def findDisappearedNumbers(self, nums: List[int]) -> List[int]: + #using the array as set itself + + result = [] + + shift = 8//2 #(range//2) + + for i in range(len(nums)): + nums[i] = nums[i]+shift #this should be range/2 + + for i in range(len(nums)): + idx = abs(nums[i])-1 #the no.s actual index in the array from 1 to N, 4 will be 3 + #1 will be 0 and so on. + if nums[idx] > 0: + nums[idx] *= -1 #mark the number at that idx negative + + for i in range(len(nums)): + if nums[i] > 0: + result.append(i+1-shift) + + return result \ No newline at end of file diff --git a/problem32.py b/problem32.py new file mode 100644 index 00000000..0134ca18 --- /dev/null +++ b/problem32.py @@ -0,0 +1,37 @@ +#find min and max in an array +#if we compare each and every element with the min and max values, then its 2N comparison so instead of that take pairs, +#there will be n//2 pairs and each pair will have 3 comparisons worse case so thats 1.5N comparisons. +#so think in pairs here +from typing import List + +class Solution: + def findMinandMax(self, nums: List[int]): + + if not nums: + return [-1, -1] + + n = len(nums) + + max_val = float('-inf') + min_val = float('inf') + + i = 0 + + while i <= n-2: + if nums[i] > nums[i+1]: + max_val = max(max_val, nums[i]) + min_val = min(min_val, nums[i+1]) + else: + max_val = max(max_val, nums[i+1]) + min_val = min(min_val, nums[i]) + + i += 2 + + if n % 2 != 0: #handle the last element if the length is odd and not even + max_val = max(max_val, nums[-1]) + min_val = min(min_val, nums[-1]) + + return [min_val, max_val] + +# Time Complexity: O(N) +# Space Complexity: O(1) diff --git a/problem33.py b/problem33.py new file mode 100644 index 00000000..f4e9b5cc --- /dev/null +++ b/problem33.py @@ -0,0 +1,51 @@ +class Solution: + def gameOfLife(self, board: List[List[int]]) -> None: + """ + Do not return anything, modify board in-place instead. + """ + #we need to store the state change within the board itself without any external variables. + # 1 -> 0 use 2 + # 0 -> 1 use 3 + # 2, 3 indicates original states were 1 and 0 respectively. + + m = len(board) + n = len(board[0]) + + def helper(board, i, j): + #right #left. #up. #bottom. #diagonals + directions = [(0,1), (0,-1), (-1,0), (1,0), (1,1), (1,-1), (-1,1), (-1,-1)] + + count = 0 + + for dx, dy in directions: + r,c = i+dx, j+dy + if 0 <= r < m and 0 <= c < n: + if board[r][c] == 1 or board[r][c] == 2:#we just need to count alive cells + count += 1 + + return count + + #use temp state change value so that we won't lose track of original value as well + for i in range(m): + for j in range(n): + count = helper(board, i ,j) #we just need count of alive neighbors + if board[i][j] and (count < 2 or count > 3): + board[i][j] = 2 + elif not board[i][j] and count == 3: + board[i][j] = 3 + + + for i in range(m): + for j in range(n): + if board[i][j] == 2: + board[i][j] = 0 #new state + elif board[i][j] == 3: + board[i][j] = 1 #new state + +# Time Complexity: O(m*n) +# Space Complexity: O(1) + +# 1 -> 0 if neighbors < 2 alive +# 1 -> 1 if neighbors 2 or 3 alive +# 1 -> 0 if neighbors > 3 alive +# 0 -> 1 if neighbors = 3 alive \ No newline at end of file