[LeetCode解題攻略] 6. Zigzag Conversion

更新 發佈閱讀 7 分鐘

這篇部落格文章將詳細解析 LeetCode 題目 6. Zigzag Conversion。這是一道字串操作題,要求將字串以 "Z" 字形排列,再按行讀取形成新的字串。以下是此題的詳細思路和解法,幫助你有效掌握此類問題。


題目概述

題目要求給定一個字串 s 和一個整數 numRows,將字串 s 按照 Z 字形排列,然後從上到下逐行讀取,以得到最終轉換的結果。

範例:

Input: s = "PAYPALISHIRING", numRows = 3
Output: "PAHNAPLSIIGYIR"

Input: s = "PAYPALISHIRING", numRows = 4
Output: "PINALSIGYAHRPI"

我們可以將字串 "PAYPALISHIRING" 按照以下方式以 Z 字形排列:

對於 numRows = 3

P   A   H   N
A P L S I I G
Y I R

對於 numRows = 4

P     I    N
A L S I G
Y A H R
P I

最後逐行讀取即可得到結果字串。


思路與解法

這道題的核心是將字串根據 Z 字形的模式填入不同的行,並按順序讀取。以下介紹兩種解法:

  1. 模擬行走 Z 字形
  2. 直接計算索引

解法一:模擬行走 Z 字形

這是最直觀的方法,我們可以將每一行分別視為一個字串。接著,依次遍歷 s 的字符,把它們按 Z 字形填入每行。

步驟:

  1. 如果 numRows 是 1,直接返回原字串,因為無需轉換。
  2. 建立一個包含 numRows 個空字串的列表 rows
  3. 使用變數 current_row 追踪當前行,布林變數 going_down 控制方向。
  4. 當到達頂部或底部時,反向改變行進方向。
  5. 最後,把 rows 中的內容連接成新字串,作為結果。

實作 (Python):

class Solution:
def convert(self, s: str, numRows: int) -> str:
if numRows == 1 or numRows >= len(s):
return s

rows = [''] * numRows
current_row, going_down = 0, False

for char in s:
rows[current_row] += char
if current_row == 0 or current_row == numRows - 1:
going_down = not going_down
current_row += 1 if going_down else -1

return ''.join(rows)

複雜度分析:

  • 時間複雜度:O(n),其中 n 是字串長度,因為我們需要遍歷每個字符。
  • 空間複雜度:O(n),儲存每一行的字串。

這是性能不錯且易於理解的解法,適合大多數情況。


解法二:直接計算索引

這個方法觀察到 Z 字形排列有一定的周期性,如果 numRows 為 3,則週期為 4。依此規律,可以直接將字符放到相應的位置,省去逐行遍歷的過程。

思路

  1. Z 字形排列的模式具有週期性。假設 numRows = 3,則每 4 個字符為一個完整的 Z 字形。
  2. 可以分成「垂直向下填充」和「向上斜線填充」兩種模式:
    • 垂直向下填充:先從上往下填滿每行。
    • 向上斜線填充:然後從底部向上填一行,直到頂部。
  3. 如果 numRows 是 1 或 numRows 大於字串長度,我們可以直接返回原字串,因為它無需變換。

實作 (Python):

class Solution:
def convert(self, s: str, numRows: int) -> str:
if numRows == 1 or numRows >= len(s):
return s

# 定義每行的容器
rows = [''] * numRows
n = len(s)
cycle_len = 2 * numRows - 2 # 每個 Z 字形週期長度

for i in range(n):
cycle_pos = i % cycle_len
if cycle_pos < numRows:
# 垂直向下填充
rows[cycle_pos] += s[i]
else:
# 斜線向上填充
rows[cycle_len - cycle_pos] += s[i]

# 將所有行合併
return ''.join(rows)

複雜度分析

  • 時間複雜度:O(n),其中 n 是字串長度,因為我們需要遍歷每個字符。
  • 空間複雜度:O(n),因為我們使用了額外的空間來儲存每行的字串內容。

總結

這道題是字串操作與數學規律結合的典型問題。以下是不同解法的適用情境:

  • 模擬行走 Z 字形:簡單直觀,適合大多數場景。
  • 直接計算索引:進階解法,適合需要減少空間使用的情況。

希望這篇解題教學能幫助你輕鬆掌握 Zigzag Conversion 的解法!


留言
avatar-img
留言分享你的想法!
avatar-img
追極光的北極熊|軟體工程師的小天地
12會員
163內容數
歡迎來到我的部落格!這裡記錄了軟體工程師的日常生活點滴,並分享程式設計與演算法的實用教學。無論你是初學者還是有經驗的開發者,都能在這裡找到深入淺出的技術解析與實戰技巧。此外,我也會分享工作中的心路歷程與學習心得,讓你不僅學到技術,更能瞭解軟體開發的實際應用與挑戰。希望透過這個平台,能與你共同成長,激發對技術的熱情!
2025/04/04
給定一個非負整數陣列 nums,其中 nums[i] 代表你在索引 i 處最多可以向右跳幾步。 請判斷是否能夠從索引 0 跳到最後一個索引。
2025/04/04
給定一個非負整數陣列 nums,其中 nums[i] 代表你在索引 i 處最多可以向右跳幾步。 請判斷是否能夠從索引 0 跳到最後一個索引。
2025/03/28
給定一個 m x n 的矩陣 matrix,請按照 螺旋順序(spiral order) 返回矩陣中的所有元素。
2025/03/28
給定一個 m x n 的矩陣 matrix,請按照 螺旋順序(spiral order) 返回矩陣中的所有元素。
2025/03/20
這道題是 LeetCode 的經典題之一,要求我們找出 一個子陣列,使其和最大,並返回這個最大和的數值。
2025/03/20
這道題是 LeetCode 的經典題之一,要求我們找出 一個子陣列,使其和最大,並返回這個最大和的數值。
看更多
你可能也想看
Thumbnail
還在煩惱平凡日常該如何增添一點小驚喜嗎?全家便利商店這次聯手超萌的馬來貘,推出黑白配色的馬來貘雪糕,不僅外觀吸睛,層次豐富的雙層口味更是讓人一口接一口!本文將帶你探索馬來貘雪糕的多種創意吃法,從簡單的豆漿燕麥碗、藍莓果昔,到大人系的奇亞籽布丁下午茶,讓可愛的馬來貘陪你度過每一餐,增添生活中的小確幸!
Thumbnail
還在煩惱平凡日常該如何增添一點小驚喜嗎?全家便利商店這次聯手超萌的馬來貘,推出黑白配色的馬來貘雪糕,不僅外觀吸睛,層次豐富的雙層口味更是讓人一口接一口!本文將帶你探索馬來貘雪糕的多種創意吃法,從簡單的豆漿燕麥碗、藍莓果昔,到大人系的奇亞籽布丁下午茶,讓可愛的馬來貘陪你度過每一餐,增添生活中的小確幸!
Thumbnail
Leetcode #1945. Sum of Digits of String After Convert 給定一個由小寫字母組成的字串 s ,以及一個整數 k 。 首先,用英文字母順序的位置替換每個字母,將 s 轉換 為整數 並且計算digits sum,反覆迭代k次。
Thumbnail
Leetcode #1945. Sum of Digits of String After Convert 給定一個由小寫字母組成的字串 s ,以及一個整數 k 。 首先,用英文字母順序的位置替換每個字母,將 s 轉換 為整數 並且計算digits sum,反覆迭代k次。
Thumbnail
題目敘述 題目會給定我們兩個字串。 第一個是指定順序的字串order。 第二個是輸入字串s。 要求我們依據order給定的順序,重新排列s。 如果出現order中沒有出現的字母,任意位置皆可。 合法答案可能不只一組,輸出其中一種即可。 題目的原文敘述 測試範例 Example
Thumbnail
題目敘述 題目會給定我們兩個字串。 第一個是指定順序的字串order。 第二個是輸入字串s。 要求我們依據order給定的順序,重新排列s。 如果出現order中沒有出現的字母,任意位置皆可。 合法答案可能不只一組,輸出其中一種即可。 題目的原文敘述 測試範例 Example
Thumbnail
題目敘述 題目會給我們一個字串s。 要求我們移除字串中的星號,還有刪除星號左手邊最靠近的第一個字元。 以字串的形式返回輸出答案。 題目的原文敘述 測試範例 Example 1: Input: s = "leet**cod*e" Output: "lecoe" Explanation:
Thumbnail
題目敘述 題目會給我們一個字串s。 要求我們移除字串中的星號,還有刪除星號左手邊最靠近的第一個字元。 以字串的形式返回輸出答案。 題目的原文敘述 測試範例 Example 1: Input: s = "leet**cod*e" Output: "lecoe" Explanation:
Thumbnail
題目敘述 題目會給定一個輸入字串s和一套編碼規則,要求我們針對字串s進行解碼,並且以字串的形式返回答案。 編碼規則: 數字[字串] -> []內的字串以對應倍數做展開,而且允許巢狀編碼。 例如: 3[a] 解碼完就是 aaa 2[bc] 解碼完就是 bcbc 2[a2[b]] = 2
Thumbnail
題目敘述 題目會給定一個輸入字串s和一套編碼規則,要求我們針對字串s進行解碼,並且以字串的形式返回答案。 編碼規則: 數字[字串] -> []內的字串以對應倍數做展開,而且允許巢狀編碼。 例如: 3[a] 解碼完就是 aaa 2[bc] 解碼完就是 bcbc 2[a2[b]] = 2
Thumbnail
題目敘述 題目會給定我們一個字串s,要求我們反轉字串s中所有母音字元的順序,並且以字串的形式輸出。 註: 母音字元為a, e, i, o, u 或者 A, E, I, O, U 題目的原文敘述 測試範例 Example 1: Input: s = "hello" Output: "ho
Thumbnail
題目敘述 題目會給定我們一個字串s,要求我們反轉字串s中所有母音字元的順序,並且以字串的形式輸出。 註: 母音字元為a, e, i, o, u 或者 A, E, I, O, U 題目的原文敘述 測試範例 Example 1: Input: s = "hello" Output: "ho
Thumbnail
題目敘述 題目會給定我們兩個字串word1 和 word2。 允許我們不限制次數進行下列兩種操作: 任意調換其中兩個字元的位置。 把字串中的某個字元全部置換成另一個字元,同時把另一個字元同時置換成某個字元。(例如把字串中原本的a都換成b,把原本的b都換成a) 問我們能不能通過上述兩項操作,
Thumbnail
題目敘述 題目會給定我們兩個字串word1 和 word2。 允許我們不限制次數進行下列兩種操作: 任意調換其中兩個字元的位置。 把字串中的某個字元全部置換成另一個字元,同時把另一個字元同時置換成某個字元。(例如把字串中原本的a都換成b,把原本的b都換成a) 問我們能不能通過上述兩項操作,
Thumbnail
題目敘述 題目會給我們兩個字串作為輸入,分別是字串s和字串t,問我最少要做幾次字元轉換,讓字串t和字串s成為Anagram"同字母異序詞"? 註: 例如 god 和 dog 就是 Anagram 同字母異序詞,也是就說,組成字母相同,但是順序可以重新排列。 題目的原文敘述 測試範例 Ex
Thumbnail
題目敘述 題目會給我們兩個字串作為輸入,分別是字串s和字串t,問我最少要做幾次字元轉換,讓字串t和字串s成為Anagram"同字母異序詞"? 註: 例如 god 和 dog 就是 Anagram 同字母異序詞,也是就說,組成字母相同,但是順序可以重新排列。 題目的原文敘述 測試範例 Ex
追蹤感興趣的內容從 Google News 追蹤更多 vocus 的最新精選內容追蹤 Google News