当前位置: 首页 > news >正文

6.3 模拟专题:LeetCode 6. Z 字形变换

1. 题目链接

LeetCode 6. Zigzag Conversion


2. 题目描述

将一个给定字符串 s 按照指定的行数 numRows 进行 Z 字形排列后,逐行读取并返回新的字符串。
示例

  • 输入:s = "PAYPALISHIRING", numRows = 3 → 输出:"PAHNAPLSIIGYIR"
  • 输入:s = "A", numRows = 1 → 输出:"A"

3. 示例分析
  1. 标准 Z 字形排列
    • 输入 s = "PAYPALISHIRING", numRows = 3 的排列如下:
      P   A   H   N  
      A P L S I I G  
      Y   I   R  
      
    • 按行读取结果为 "PAHNAPLSIIGYIR"
  2. 单行排列
    • 输入 s = "ABCD", numRows = 1 → 输出 "ABCD"
  3. 两行排列
    • 输入 s = "ABCDE", numRows = 2 → 排列为 A C EB D,结果为 "ACEB D"(忽略空格)。

4. 算法思路

核心思想数学规律 + 直接构造

  1. 周期分析
    • Z 字形排列的每个周期长度为 d = 2 * numRows - 2。例如,numRows = 3 时,周期为 4。
  2. 行遍历规则
    • 首行和末行:每个周期仅包含一个字符,位置分别为 jj + numRows - 1
    • 中间行:每个周期包含两个字符,位置分别为 j + ij + d - ii 为当前行号)。
  3. 逐行构造
    • 遍历每一行,根据周期规律直接计算字符位置并拼接结果。

5. 边界条件与注意事项
  1. 单行处理
    • numRows = 1 时,直接返回原字符串。
  2. 空字符串处理
    • s 为空,返回空字符串。
  3. 字符位置越界
    • 在中间行遍历时,需确保计算的字符位置不超过字符串长度。
  4. 周期完整性
    • 每个周期的两个字符可能不全存在(如字符串长度不足),需分别判断。

6. 代码实现
class Solution {
public:
    string convert(string s, int numRows) {
        if (numRows == 1) return s; // 单行直接返回
        
        string ret;
        int n = s.size();
        int d = 2 * numRows - 2; // 周期长度
        
        for (int i = 0; i < numRows; i++) {
            if (i == 0) { // 首行
                for (int j = 0; j < n; j += d) {
                    ret += s[j];
                }
            } else if (i == numRows - 1) { // 末行
                for (int j = i; j < n; j += d) {
                    ret += s[j];
                }
            } else { // 中间行
                for (int j = i, k = d - i; j < n || k < n; j += d, k += d) {
                    if (j < n) ret += s[j];
                    if (k < n) ret += s[k];
                }
            }
        }
        return ret;
    }
};

在这里插入图片描述


关键代码解析

  1. 周期计算

    int d = 2 * numRows - 2;
    
    • 每个 Z 字形周期的字符数为 2 * numRows - 2
  2. 首行处理

    for (int j = 0; j < n; j += d) {
        ret += s[j];
    }
    
    • 首行字符位置为 0, d, 2d, ...
  3. 末行处理

    for (int j = i; j < n; j += d) {
        ret += s[j];
    }
    
    • 末行字符位置为 numRows - 1, numRows - 1 + d, ...
  4. 中间行处理

    for (int j = i, k = d - i; j < n || k < n; j += d, k += d) {
        if (j < n) ret += s[j];
        if (k < n) ret += s[k];
    }
    
    • 中间行的两个字符位置分别为 i, i + d, ...d - i, d - i + d, ...

总结

直接构造法通过数学规律确定 Z 字形排列中每行字符的位置,以线性时间复杂度和空间复杂度高效解决问题。其核心在于 周期分析与位置计算,避免了模拟排列的额外空间消耗。

适用场景

  • 字符串长度较大(n ≤ 1e3)。
  • 需要保证代码高效性和简洁性。

关键点

  • 理解 Z 字形排列的周期性规律。
  • 处理中间行时的双指针遍历逻辑。

相关文章:

  • Vue3 知识点总结
  • 在 PostgreSQL 中设置调试环境以更好地理解 OpenSSL API
  • DeepSeek 助力 Vue3 开发:打造丝滑的表格(Table)之添加行拖拽排序功能示例1,TableView16_01.vue 基础行拖拽排序示例
  • cnn中的dropout技术
  • 如何在jupyter notebook中使用django框架
  • Linux 配置时间服务器
  • 企业级全栈开发终极指南:Spring Boot+Vue3+Kubernetes实战,从0到上线高并发系统
  • 禾赛盈利了,但激光雷达没有胜利
  • 基于web的家政服务网站
  • JPA实体类注解缺失异常全解:从报错到防御!!!
  • 【CF】Day15——Codeforces Round 1012 (Div. 2) CD
  • 【微服务架构】故障转移策略的理解及手写实现
  • C++ STL 序列式容器之(三)-- List
  • 【模型压缩+推理加速】知识蒸馏综述解读
  • 第四章 异常处理
  • 基于大模型的结核性胸膜炎风险预测及临床方案研究报告
  • CF2041C Cube
  • 《Operating System Concepts》阅读笔记:p481-p482
  • stanley 路径跟踪控制算法
  • 从概率到梯度:理解分类问题中交叉熵的优越性
  • 东莞网站建设(曼哈顿信科)/建立一个网站需要花多少钱
  • 室内设计网站配色app/首页排名优化公司
  • 网站如何做a b测试/seo网络优化是什么意思
  • 文明网站建设情况/河南郑州最近的热搜事件
  • dw企业网站设计/南宁seo营销推广
  • 上海市公安网站备案/十大免费无代码开发软件