The string "PAYPALISHIRING"
is written in a zigzag pattern on a given number of rows like this: (you may want to display this pattern in a fixed font for better legibility)
P A H N A P L S I I G Y I RAnd then read line by line:
"PAHNAPLSIIGYIR"
Write the code that will take a string and make this conversion given a number of rows:
string convert(string text, int nRows);
convert("PAYPALISHIRING", 3)
should return
"PAHNAPLSIIGYIR"
.
解法一:
维持一个数组StringBuilder[],将给定的String s 按照题目中所示的方法把每一个字符依次存进对应的行的StringBuilder中,在存的过程中有两种情况,一是竖直向下,一是斜向右上。最后将数组每一个index的字符串加在一起。时间复杂度 O(n).
代码如下:
public String convert(String s, int numRows) {
char[] ss = s.toCharArray();
int len = ss.length;
StringBuilder[] sb = new StringBuilder[numRows];
for (int i = 0; i < numRows; i++){
sb[i] = new StringBuilder();
}
int index = 0;
while (index < len){
for (int i = 0; i < numRows && index < len; i++){
sb[i].append(ss[index++]);
}
for (int i = numRows - 2; i >= 1 && index < len; i--){
sb[i].append(ss[index++]);
}
}
for (int i = 1; i < sb.length; i++){
sb[0].append(sb[i]);
}
return sb[0].toString();
}
第一行和最后一行每一个元素current 和 next 相隔的距离一样,都是step = numRows * 2 - 2. 介于第一行和最后一行之间的,不仅要存vertical方向上的元素,还要存其对角线方向上的neighbor,并且这两个元素和各自对应的下一个周期一样(step = numRows * 2 - 2). 我们可以维持一个stringbuilder,先加第一行,再加第二行和倒数第二行,再加最后一行。时间复杂度 O(n)
代码如下:
public String convert(String s, int numRows) {
if (s == null || s.length() == 0 || numRows <= 1 || s.length() <= numRows){
return s;
}
char[] ss = s.toCharArray();
int len = ss.length, step = numRows * 2 - 2;
StringBuilder sb = new StringBuilder();
// first row
for (int i = 0; i < len; i += step){
sb.append(ss[i]);
}
// rows between 1st row and last row
for (int rowIndex = 1; rowIndex < numRows - 1; rowIndex++){
int verticalIndex = rowIndex;
int nextIndex = step - verticalIndex;
while (verticalIndex < len){
sb.append(ss[verticalIndex]);
verticalIndex += step;
if (nextIndex < len){
sb.append(ss[nextIndex]);
nextIndex += step;
}
}
}
// last row
for (int i = numRows - 1; i < len; i += step){
sb.append(ss[i]);
}
return sb.toString();
}
此解法的运行时间少于解法一
两个解法的思路均来源于leetcode discussion.