自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

Python 面試高頻算法題,這五個你應(yīng)該掌握!

開發(fā)
很多公司都會通過算法題來篩選出優(yōu)秀的工程師。本文將為大家總結(jié)Python面試中最??嫉奈鍌€算法題。

在Python求職面試中,算法題是考察候選人編程能力和解決問題能力的重要環(huán)節(jié)。很多公司都會通過算法題來篩選出優(yōu)秀的工程師。本文將為大家總結(jié)Python面試中最常考的五個算法題。

1. 兩數(shù)之和 (Two Sum)

題目描述: 給定一個整數(shù)數(shù)組 nums 和一個整數(shù)目標(biāo)值 target,請你在該數(shù)組中找出和為目標(biāo)值 target 的那兩個整數(shù),并返回它們的數(shù)組下標(biāo)。你可以假設(shè)每種輸入只會對應(yīng)一個答案,并且數(shù)組中同一個元素不能使用兩遍。

解題思路:

最直觀的方法是使用兩層循環(huán)遍歷數(shù)組,檢查每兩個數(shù)字的和是否等于目標(biāo)值。但這種方法的時間復(fù)雜度為 O(n^2)。

更高效的方法是使用哈希表(字典)來存儲已經(jīng)遍歷過的數(shù)字及其下標(biāo)。在遍歷數(shù)組的過程中,對于每個數(shù)字 num,我們檢查 target - num 是否在哈希表中。如果在,則說明我們找到了這兩個數(shù)字,直接返回它們的下標(biāo)即可。否則,將當(dāng)前的 num 和它的下標(biāo)存入哈希表中。這種方法的時間復(fù)雜度為 O(n)。

def two_sum(nums, target):
    """
    找出數(shù)組中和為目標(biāo)值的兩個數(shù)的下標(biāo)

    Args:
        nums: 整數(shù)數(shù)組
        target: 目標(biāo)值

    Returns:
        包含兩個下標(biāo)的列表,如果不存在則返回 None
    """
    num_map = {}  # 創(chuàng)建一個空字典用于存儲數(shù)字和它們的下標(biāo)
    for index, num in enumerate(nums):
        complement = target - num  # 計算與當(dāng)前數(shù)字配對的另一個數(shù)字
        if complement in num_map:  # 檢查complement是否已在字典中
            return [num_map[complement], index]  # 如果在,返回complement的下標(biāo)和當(dāng)前數(shù)字的下標(biāo)
        num_map[num] = index  # 如果不在,將當(dāng)前數(shù)字和它的下標(biāo)存入字典
    returnNone# 如果遍歷完數(shù)組沒有找到符合條件的兩個數(shù),返回 None

# 案例
nums = [2, 7, 11, 15]
target = 9
result = two_sum(nums, target)
print(f"數(shù)組:{nums},目標(biāo)值:{target},結(jié)果:{result}")  # 輸出:數(shù)組:[2, 7, 11, 15],目標(biāo)值:9,結(jié)果:[0, 1]

nums = [3, 2, 4]
target = 6
result = two_sum(nums, target)
print(f"數(shù)組:{nums},目標(biāo)值:{target},結(jié)果:{result}")  # 輸出:數(shù)組:[3, 2, 4],目標(biāo)值:6,結(jié)果:[1, 2]

2. 反轉(zhuǎn)鏈表 (Reverse Linked List)

題目描述: 給你單鏈表的頭節(jié)點 head ,請你反轉(zhuǎn)鏈表,并返回反轉(zhuǎn)后的鏈表頭節(jié)點。

解題思路:反轉(zhuǎn)鏈表的核心思想是改變鏈表中節(jié)點的指向。我們可以使用迭代或遞歸兩種方法來實現(xiàn)。

迭代法:

維護三個指針:prev(指向前一個節(jié)點,初始為 None),curr(指向當(dāng)前節(jié)點,初始為 head),next_node(指向下一個節(jié)點)。

遍歷鏈表,對于每個當(dāng)前節(jié)點 curr,先保存它的下一個節(jié)點 next_node。然后將 curr 的 next 指針指向 prev。接著,將 prev 移動到 curr,curr 移動到 next_node。當(dāng) curr 為 None 時,prev 就指向了反轉(zhuǎn)后的鏈表的頭節(jié)點。

class ListNode:
    def __init__(self, val=0, next=None):
        self.val = val
        self.next = next

def reverse_linked_list(head):
    """
    反轉(zhuǎn)單鏈表

    Args:
        head: 鏈表的頭節(jié)點

    Returns:
        反轉(zhuǎn)后鏈表的頭節(jié)點
    """
    prev = None# 前一個節(jié)點,初始為 None
    curr = head  # 當(dāng)前節(jié)點,初始為頭節(jié)點
    while curr:
        next_node = curr.next  # 保存下一個節(jié)點
        curr.next = prev  # 將當(dāng)前節(jié)點的 next 指針指向前一個節(jié)點
        prev = curr  # 將 prev 移動到當(dāng)前節(jié)點
        curr = next_node  # 將 curr 移動到下一個節(jié)點
    return prev  # 當(dāng) curr 為 None 時,prev 就是反轉(zhuǎn)后的頭節(jié)點

# 案例
# 創(chuàng)建鏈表:1 -> 2 -> 3 -> 4 -> 5
head = ListNode(1)
head.next = ListNode(2)
head.next.next = ListNode(3)
head.next.next.next = ListNode(4)
head.next.next.next.next = ListNode(5)

def print_linked_list(head):
    while head:
        print(head.val, end=" -> ")
        head = head.next
    print("None")

print("原始鏈表:", end="")
print_linked_list(head)

reversed_head = reverse_linked_list(head)

print("反轉(zhuǎn)后鏈表:", end="")
print_linked_list(reversed_head)

3. 二分查找 (Binary Search)

題目描述: 給定一個有序整數(shù)數(shù)組 nums 和一個目標(biāo)值 target,請你在該數(shù)組中搜索目標(biāo)值。如果目標(biāo)值存在返回它的下標(biāo),否則返回 -1。

二分查找是一種高效的搜索算法,適用于已排序的數(shù)組。其基本思想是:

  • 找到數(shù)組的中間元素。
  • 如果中間元素等于目標(biāo)值,則返回中間元素的下標(biāo)。
  • 如果中間元素小于目標(biāo)值,則在數(shù)組的右半部分繼續(xù)搜索。
  • 如果中間元素大于目標(biāo)值,則在數(shù)組的左半部分繼續(xù)搜索。

重復(fù)以上步驟,直到找到目標(biāo)值或搜索范圍為空。

def binary_search(nums, target):
    """
    在有序數(shù)組中查找目標(biāo)值

    Args:
        nums: 有序整數(shù)數(shù)組
        target: 目標(biāo)值

    Returns:
        目標(biāo)值的下標(biāo),如果不存在則返回 -1
    """
    left, right = 0, len(nums) - 1# 初始化左右指針
    while left <= right:
        mid = (left + right) // 2# 計算中間元素的下標(biāo)
        if nums[mid] == target:
            return mid  # 找到目標(biāo)值,返回下標(biāo)
        elif nums[mid] < target:
            left = mid + 1# 目標(biāo)值在右半部分,移動左指針
        else:
            right = mid - 1# 目標(biāo)值在左半部分,移動右指針
    return-1# 如果循環(huán)結(jié)束沒有找到目標(biāo)值,返回 -1

# 案例
nums = [-1, 0, 3, 5, 9, 12]
target = 9
result = binary_search(nums, target)
print(f"數(shù)組:{nums},目標(biāo)值:{target},結(jié)果:{result}")  # 輸出:數(shù)組:[-1, 0, 3, 5, 9, 12],目標(biāo)值:9,結(jié)果:4

nums = [-1, 0, 3, 5, 9, 12]
target = 2
result = binary_search(nums, target)
print(f"數(shù)組:{nums},目標(biāo)值:{target},結(jié)果:{result}")  # 輸出:數(shù)組:[-1, 0, 3, 5, 9, 12],目標(biāo)值:2,結(jié)果:-1

4. 合并兩個有序鏈表 (Merge Two Sorted Lists)

題目描述: 將兩個升序鏈表合并為一個新的 升序 鏈表并返回。新鏈表是通過拼接給定的兩個鏈表的所有節(jié)點組成的。

解題思路:

我們可以創(chuàng)建一個新的鏈表,并通過比較兩個輸入鏈表的當(dāng)前節(jié)點的值,將較小的節(jié)點添加到新鏈表中。

維護一個指向新鏈表尾部的指針 tail 和兩個指向輸入鏈表當(dāng)前節(jié)點的指針 l1 和 l2。

比較 l1 和 l2 當(dāng)前節(jié)點的值:

  • 如果 l1 為空,將 l2 的剩余部分添加到新鏈表的尾部。
  • 如果 l2 為空,將 l1 的剩余部分添加到新鏈表的尾部。
  • 如果 l1.val <= l2.val,將 l1 的當(dāng)前節(jié)點添加到新鏈表的尾部,并將 l1 指向下一個節(jié)點。
  • 否則,將 l2 的當(dāng)前節(jié)點添加到新鏈表的尾部,并將 l2 指向下一個節(jié)點。

重復(fù)以上步驟,直到兩個輸入鏈表都為空。為了方便操作,我們可以創(chuàng)建一個啞節(jié)點作為新鏈表的頭部。

def merge_two_lists(l1, l2):
    """
    合并兩個有序鏈表

    Args:
        l1: 第一個有序鏈表的頭節(jié)點
        l2: 第二個有序鏈表的頭節(jié)點

    Returns:
        合并后的有序鏈表的頭節(jié)點
    """
    dummy = ListNode(0)  # 創(chuàng)建一個啞節(jié)點作為新鏈表的頭部
    tail = dummy  # tail 指向新鏈表的尾部

    while l1 and l2:
        if l1.val <= l2.val:
            tail.next = l1
            l1 = l1.next
        else:
            tail.next = l2
            l2 = l2.next
        tail = tail.next  # 移動 tail 指針

    # 將剩余的鏈表添加到尾部
    if l1:
        tail.next = l1
    elif l2:
        tail.next = l2

    return dummy.next  # 返回啞節(jié)點的下一個節(jié)點,即合并后鏈表的頭節(jié)點

# 案例
# 創(chuàng)建鏈表1: 1 -> 2 -> 4
list1 = ListNode(1)
list1.next = ListNode(2)
list1.next.next = ListNode(4)

# 創(chuàng)建鏈表2: 1 -> 3 -> 4
list2 = ListNode(1)
list2.next = ListNode(3)
list2.next.next = ListNode(4)

print("鏈表1:", end="")
print_linked_list(list1)
print("鏈表2:", end="")
print_linked_list(list2)

merged_list = merge_two_lists(list1, list2)

print("合并后鏈表:", end="")
print_linked_list(merged_list)

5. 有效的括號 (Valid Parentheses)

題目描述: 給定一個只包括 '(',')','{','}','[',']' 的字符串 s ,判斷字符串是否有效。

有效字符串需滿足:

  • 左括號必須用相同類型的右括號閉合。
  • 左括號必須以正確的順序閉合。

解題思路:

這道題可以使用棧(Stack)來解決。遍歷字符串中的每個字符:

  • 如果遇到左括號('(', '[', '{'),將其壓入棧中。
  • 如果遇到右括號(')', ']', '}'),檢查棧是否為空。如果為空,則說明沒有對應(yīng)的左括號,字符串無效。否則,彈出棧頂?shù)脑?,判斷它是否與當(dāng)前的右括號匹配。如果不匹配,則字符串無效。

遍歷完字符串后,如果棧為空,則說明所有括號都正確閉合,字符串有效。否則,說明還有未閉合的左括號,字符串無效。

def is_valid(s):
    """
    判斷字符串中的括號是否有效

    Args:
        s: 包含括號的字符串

    Returns:
        True 如果字符串有效,F(xiàn)alse 否則
    """
    stack = []  # 創(chuàng)建一個空棧
    mapping = {")": "(", "]": "[", "}": "{"}  # 定義右括號和對應(yīng)的左括號

    for char in s:
        if char in mapping:  # 如果是右括號
            top_element = stack.pop() if stack else'#'# 如果棧為空,pop會報錯,用 '#' 代替
            if mapping[char] != top_element:
                returnFalse# 棧頂元素與當(dāng)前右括號不匹配,返回 False
        else:  # 如果是左括號,壓入棧中
            stack.append(char)

    returnnot stack  # 如果棧為空,說明所有括號都正確閉合,返回 True

# 案例
s = "()"
result = is_valid(s)
print(f"字符串:'{s}',是否有效:{result}")  # 輸出:字符串:'()',是否有效:True

s = "()[]{}"
result = is_valid(s)
print(f"字符串:'{s}',是否有效:{result}")  # 輸出:字符串:'()[]{}',是否有效:True

s = "(]"
result = is_valid(s)
print(f"字符串:'{s}',是否有效:{result}")  # 輸出:字符串:'(]',是否有效:False

s = "([)]"
result = is_valid(s)
print(f"字符串:'{s}',是否有效:{result}")  # 輸出:字符串:'([)]',是否有效:False

s = "{[]}"
result = is_valid(s)
print(f"字符串:'{s}',是否有效:{result}")  # 輸出:字符串:'{[]}',是否有效:True

總結(jié)

掌握這些常見的算法題對于Python面試至關(guān)重要。通過理解每道題的解題思路、掌握相應(yīng)的代碼實現(xiàn),并進(jìn)行大量的練習(xí),將會更有信心應(yīng)對面試中的算法挑戰(zhàn)。

責(zé)任編輯:趙寧寧 來源: Python數(shù)智工坊
相關(guān)推薦

2020-08-11 17:14:31

數(shù)據(jù)庫SQL技術(shù)

2021-08-09 14:47:34

Go語言開發(fā)

2020-08-06 08:27:21

JavaScript概念語言

2019-11-26 10:30:11

CSS前端面試題

2019-12-25 14:19:21

Python編程語言Java

2020-04-22 13:41:33

數(shù)據(jù)結(jié)構(gòu)大數(shù)據(jù)數(shù)據(jù)

2017-05-17 17:23:00

2015-12-04 10:23:47

2023-11-15 07:54:03

HashMap數(shù)據(jù)結(jié)構(gòu)

2024-11-11 17:24:09

2013-01-18 08:53:27

Android開發(fā)學(xué)習(xí)Android

2016-07-22 15:22:52

2024-04-16 00:00:00

Spring微服務(wù)架構(gòu)

2023-10-14 18:22:15

開發(fā)工具前端

2015-06-15 09:49:22

Docker開源平臺虛擬化容器

2019-08-19 00:56:07

TCPIP協(xié)議內(nèi)部網(wǎng)

2024-08-13 15:09:41

2022-01-18 16:42:03

區(qū)塊鏈加密信息資源

2024-07-22 00:00:00

2017-11-02 06:18:26

點贊
收藏

51CTO技術(shù)棧公眾號