数组-简单

1、面试题 17.10. 主要元素 https://leetcode-cn.com/problems/find-majority-element-lcci/

考点:

class Solution:
    def majorityElement(self, nums: List[int]) -> int:
        eles = set(nums)
        all_length = len(nums)
        for ele in eles:
            if nums.count(ele) >= all_length/2:
                return ele
        return -1

2、面试题4. 二维数组中的查找

class Solution:
    def findNumberIn2DArray(self, matrix: List[List[int]], target: int) -> bool:
        if not matrix:
            return False
        row = len(matrix)
        col = len(matrix[0])
        if row == 1 and col == 0:
            return False
        
        data = []
        for i in range(row):
            data.extend(matrix[i])
        data = set(data)
        return target in data

3、面试题 16.06. 最小差

class Solution:
    def smallestDifference(self, a: List[int], b: List[int]) -> int:
        if not a or not b:
            return None
        a.sort()
        b.sort()
        len_a = len(a)
        len_b = len(b)

        cur_a = 0
        cur_b = 0
        
        min_abs = 2147483647 * 2
        while cur_a < len_a and cur_b < len_b:
            if abs(a[cur_a] - b[cur_b]) < min_abs:
                min_abs = abs(a[cur_a] - b[cur_b])
            
            if a[cur_a] > b[cur_b]:
                cur_b += 1
            else:
                cur_a += 1
        return min_abs

4、面试题 16.10. 生存人数

考点:

1、想到有一道坐公交的题,和这个类似,用一个数组表示所有年份,然后一个人一生在所有年份加1; 最后就可以直接返回 人数最多年份

class Solution:
    def maxAliveYear(self, birth: List[int], death: List[int]) -> int:
        years = [0] * 101
        for i in range(len(birth)):
            b = birth[i] - 1900
            d = death[i] - 1900
            
            for k in range(b, d + 1):
                years[k] += 1
        # print(years)
        return years.index(max(years)) + 1900

5、面试题 16.20. T9键盘

考点:

1、逆向思维,由 字符窜 反推 数字组合

class Solution:
    def getValidT9Words(self, num: str, words: List[str]) -> List[str]:
        keyb = {"a":2, "b":2, "c":2, "d":3, "e":3, "f":3, "g":4, "h":4, "i":4, "j":5, "k":5, "l":5, "m":6, "n":6, "o":6, "p":7, "q":7, "r":7, "s":7, "t":8, "u":8, "v":8, "w":9, "x":9, "y":9, "z":9}

        result = []
        for word in words:
            num_list = ""
            for ch in word:
                num_list += str(keyb[ch])
            if num_list in num:
                result.append(word)
        return result

6、面试题 17.05. 字母与数字

考点:

1、前缀和,相对正常前缀和,拐了个弯,按照数字是+1,字母是-1,求数组的前缀和

2、数组最后出现位置计算,先把数组求reverse().再使用index计算

3、注意,本题有个坑是,数字可能是多个数字组合的字符串,需要按下图绿色处理

class Solution:
    def findLongestSubarray(self, array: List[str]) -> List[str]:
        array_len = len(array)
        new_array = [0] * (array_len +1)
        cur = 0
        for i in range(array_len):
            #数字+1, 字母-1
            if array[i].startswith("1") or array[i].startswith("0") or array[i].startswith("2") or array[i].startswith("3") or array[i].startswith("4") or array[i].startswith("5") or array[i].startswith("6") or array[i].startswith("7") or array[i].startswith("8") or array[i].startswith("9"):
                cur += 1
            else:
                cur += -1
            new_array[i+1] = cur
        
        new_array_reverse = list(new_array)
        new_array_reverse.reverse()

        # 值相等,表示中间结果值为0
        max_len = 0
        start = 0
        end = 0
        matched = []
        for i in range(array_len):
            try:
                # if new_array[i] in matched:
                #     continue
                r_value = array_len - new_array_reverse.index(new_array[i])
                matched.append(new_array[i])
                if r_value -i-1  > max_len:
                    max_len = r_value - i -1
                    start = i
                    end = r_value
            except Exception as e:
                continue
        return array[start: end]

  其实按照上面做,会出现超时,几个用例跑不完,加入如下优化进行剪枝

class Solution:
    def findLongestSubarray(self, array: List[str]) -> List[str]:
        array_len = len(array)
        new_array = [0] * (array_len +1)
        cur = 0
        for i in range(array_len):
            #数字+1, 字母-1
            if array[i].startswith("1") or array[i].startswith("0") or array[i].startswith("2") or array[i].startswith("3") or array[i].startswith("4") or array[i].startswith("5") or array[i].startswith("6") or array[i].startswith("7") or array[i].startswith("8") or array[i].startswith("9"):
                cur += 1
            else:
                cur += -1
            new_array[i+1] = cur
        
        new_array_reverse = list(new_array)
        new_array_reverse.reverse()

        # 值相等,表示中间结果值为0
        max_len = 0
        start = 0
        end = 0
        matched = []
        for i in range(array_len):
            try:
                if new_array[i] in matched:   # 同一个前缀和,前面是按照最前面和最后面计算,肯定比现在计算的长,所有不用重复计算
                     continue
                r_value = array_len - new_array_reverse.index(new_array[i])
                matched.append(new_array[i])
                if r_value -i-1  > max_len:
                    max_len = r_value - i -1
                    start = i
                    end = r_value
            except Exception as e:
                continue
        return array[start: end] 

7、面试题 16.24. 数对和

1、首先想到就是从前往后,使用index一个一个匹配,然后就超时了

class Solution:
    def pairSums(self, nums: List[int], target: int) -> List[List[int]]:
        # 不存在同一个值 属于多个结果对得情况
        nums_len = len(nums)
        result = []
        matched = set()
        pair = {}
        for i in range(nums_len):
            if i in matched:
                continue
            find_value = target - nums[i]
            print(i)
            try:
                start = i + 1
                while True:
                    print(find_value)
                    find = nums.index(find_value, start)
                    if find in matched:
                        start = find +1
                        continue
                    else:
                        break
                # print(find)
                matched.add(find)
                result.append([nums[i], nums[find]])
            except:
                continue
            
        return result

 

以后对于碰到数字数组这种题,如果对于顺序没有要求,只要求 数字对,可以先使用排序

对于此题,在排完序之后,直接使用左右指针即可

class Solution:
    def pairSums(self, nums: List[int], target: int) -> List[List[int]]:
        # 不存在同一个值 属于多个结果对得情况
        nums.sort()
        nums_len = len(nums)
        result = []
        left = 0
        right = nums_len - 1
        while left < right:
            if nums[left] + nums[right] == target:
                result.append([nums[left], nums[right]])
                left = left + 1
                right = right - 1
                
            elif nums[left] + nums[right] > target:
                right = right - 1
            else:
                left += 1
            
        return result

8、面试题 01.08. 零矩阵

考点:

class Solution:
    def setZeroes(self, matrix: List[List[int]]) -> None:
        """
        Do not return anything, modify matrix in-place instead.
        """
        if not matrix:
            return matrix
        row = len(matrix)
        col = len(matrix[0])
        print(row, col)
        zero_row = []
        zero_col = []
        for i in range(row):
            for j in range(col):
                if matrix[i][j] == 0:
                    zero_row.append(i)
                    zero_col.append(j)
        
        for irow in zero_row:
            for j in range(col):
                matrix[irow][j] = 0

        for col in zero_col:
            print("*", row)
            for j in range(row):
                print(j)
                matrix[j][col] = 0
        return matrix

9、面试题 16.04. 井字游戏

考点:

1、行判断是否相同使用len(set)

2、注意 都是空白的,不能返回

class Solution:
    def tictactoe(self, board: List[str]) -> str:
        n = len(board)
        for i in range(n):
            if len(set(board[i])) == 1 and (board[i][0] == "X" or board[i][0] == "O"):
                return board[i][0]
            col_set = set()
            same = True
            for j in range(1, n):
                if not board[0][i] == board[j][i]:
                    same = False
                    break
            if same and (board[0][i] == "X" or board[0][i] == "O"):
                return board[0][i]
            
        same = True
        for i in range(1, n):
            if not board[i][i] == board[0][0]:
                same = False
                break
        if same and (board[0][0] == "X" or board[0][0] == "O"):
            return board[0][0]
        
        same = True
        for i in range(1, n):
            if not board[0][n-1] == board[i][n-i-1]:
                same = False
                break
        if same and (board[0][n-1] == "X" or board[0][n-1] == "O"):
            return board[0][n-1]

        for i in range(n):
            if " " in board[i]:
                return "Pending"
        
        return "Draw"

9、面试题 16.16. 部分排序

1、从头开始遍历,先找到start,然后从最后开始,找到end位置, 然后 就超时了

class Solution:
    def subSort(self, array: List[int]) -> List[int]:
        start = -1
        end = -1
        for i in range(len(array)): 
            print(i)          
            if array[i+1:]:
                if array[i] > min(array[i+1:]):
                    start = i
                    break
        
        if not start == -1:
            for i in range(len(array)-1, start, -1):
                print(i)
                if array[:i]:
                    if array[i] < max(array[:i]):
                        end = i
                        break
                
            
            return [start, end]
        else:
            return [-1, -1]

老办法,先对数字数组进行排序,再使用 看是否提高效率。 此处 排序之后数组可以直接对比对应位置值,不用每次的min求值,提高效率

class Solution:
    def subSort(self, array: List[int]) -> List[int]:
        sort_array = sorted(array)
        start = -1
        end = -1
        for i in range(len(array)):
            if not array[i] == sort_array[i]:
                start = i
                break

        if not start == -1:
            for i in range(len(array)-1, start, -1):
                if not array[i] == sort_array[i]:
                    end = i
                    break
            return [start, end]
        else:
            return [-1, -1]

10、面试题 01.07. 旋转矩阵

考点:

1、先换位,在翻转,有些考数学或者 脑筋急转弯

class Solution:
    def rotate(self, matrix: List[List[int]]) -> None:
        """
        Do not return anything, modify matrix in-place instead.
        """
        for i in range(len(matrix)):
            for j in range(i, len(matrix[0])):
                matrix[i][j], matrix[j][i] = matrix[j][i], matrix[i][j]

        # 每行翻转
        for i in range(len(matrix)):
            matrix[i].reverse()

11、 面试题 08.04. 幂集

考点:

1、薛定谔的猫,每个事物都是2种态,存在 or 不存在; 所以该题对每个元素 都进行 存在 or 不存在赋值。 保留原数组为不存在情况,按照原数组都按照当前值对所有数组进行赋值为 存在情况

2、注意 扩充 当值

class Solution:
    def subsets(self, nums: List[int]) -> List[List[int]]:
        results = []
        results.append([])
        for i in range(len(nums)):
            cur = nums[i]

            extend_result = []
            for result in results:
                if result:
                    tmp_results = list(result)
                    tmp_results.append(cur)
                    extend_result.append(tmp_results)
            results.append([cur])
            results.extend(extend_result)
        return results
            

12、155. 最小栈

class MinStack:

    def __init__(self):
        """
        initialize your data structure here.
        """
        self.data = []

    def push(self, x: int) -> None:
        self.data.append(x)

    def pop(self) -> None:
        if self.data:
            return self.data.pop()
        else:
            return []

    def top(self) -> int:
        if self.data:
            return self.data[-1]
        else:
            return []

    def getMin(self) -> int:
        return min(self.data)

 13、150. 逆波兰表达式求值

class Solution:
    def evalRPN(self, tokens: List[str]) -> int:
        data_stack = []
        for token in tokens:
            if token not in ["+", "-", "*", "/"]:
                data_stack.append(int(token))
            else:
                data2 = data_stack.pop()
                data1 = data_stack.pop()
                if token == "+":
                    data_stack.append(data1 + data2)
                elif token == "-":
                    data_stack.append(data1 - data2)
                elif token == "*":
                    data_stack.append(data1 * data2)
                elif token == "/":
                    data_stack.append(int(data1 / data2))
        return data_stack[-1]

  


 

 
posted @ 2020-11-21 22:55  哈哈哈喽喽喽  阅读(109)  评论(0编辑  收藏  举报