[leetcode] Z 字形变换

  1. Z 字形变换

将一个给定字符串根据给定的行数,以从上往下、从左到右进行 Z 字形排列。

比如输入字符串为 “LEETCODEISHIRING” 行数为 3 时,排列如下:

L C I R
E T O E S I I G
E D H N
之后,你的输出需要从左往右逐行读取,产生出一个新的字符串,比如:“LCIRETOESIIGEDHN”。

请你实现这个将字符串进行指定行数变换的函数:

string convert(string s, int numRows);
示例 1:

输入: s = “LEETCODEISHIRING”, numRows = 3
输出: “LCIRETOESIIGEDHN”
示例 2:

输入: s = “LEETCODEISHIRING”, numRows = 4
输出: “LDREOEIIECIHNTSG”
解释:

L D R
E O E I I
E C I H N
T S G

  1. 按行排序

    按照Z字顺序,可以知道每个字符是在从上到下,从下到上的顺序在排列,这样可以new出stringbuilder数组,按照顺序放到数组里面,即可得出答案。

      public String convert(String s, int numRows) {
             if (null == s || s.length() == 0) {
                 return s;
             }
             StringBuilder[] stringBuilders = new StringBuilder[numRows];
             // 初始化
             for (int i = 0; i < Math.min(numRows, s.length()); i++) {
                 stringBuilders[i] = new StringBuilder();
             }
             int index = 0;
             int dir = 1;
             for (char c : s.toCharArray()) {
                 stringBuilders[index].append(c);
                 index += dir;
                 if (index == 0 || index == numRows - 1) {
                     dir = -dir;
                 }
             }
             StringBuilder stringBuilder = new StringBuilder();
             for (StringBuilder stringBuilder1 : stringBuilders) {
                 stringBuilder.append(stringBuilder1);
             }
     
             return stringBuilder.toString();
         }
    
  2. 按照规律解题

    解题思路
    如果以4行为例
    L D R
    E O E I I
    E C I H N
    T S G
    可以知道前面6个字符按照重复的规律排列的
    这样就可以知道重复的规律为 2n-2
    这样知道第一行为 0,6,12,18
    则规律为6的倍数
    第二行为1,5,7,11,13,
    则规律为 06+0 1+6-1 16+1 26-1 26+1
    第三行为 2,4,8,10,14
    规律为 06+2 16-2 16+2 26-2 26+2
    第四行为 3 6 9
    规律为 0
    6+3 16+3 26+3

    组合规律为 6*(i++)-(行-1)并且不和上一次得到的数值重复即可使用

    public String convert1(String s, int numRows) {
     if (null == s || s.length() <= numRows) {
         return s;
     }
    
     // 计算重复的数字
     int repeat = 2 * numRows - 2;
    
     int lastNum = -1;
     StringBuilder stringBuilder = new StringBuilder();
     //行的循环
     for (int i = 0; i < numRows; i++) {
         int n = -1;
         int x = 0;
         int y = -1;
    
         while ((y = x / 2 * repeat + i * n) < s.length()) {
             if (y >= 0 && y != lastNum) {
                 stringBuilder.append(s.charAt(y));
             }
             lastNum = y;
             x++;
             n = -n;
         }
         lastNum = -1;
     }
    
     //获取重复的规律
     return stringBuilder.toString();
    

    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值