Z字形变换
题目:
遇到这种题有横有竖的,我首先就想到的二维数组的解法:
说是Z字形,其实更像是一下一上的重复循环,所以我们思考的是每一个循环需要多少个字符:
假设rowNum=3,那么中间就是1个,总共需要4个
假设rowNum=4,那么中间就是2个,总共需要6个
假设rowNum=5,那么中间就是3个,总共需要8个
那么很明显,一下一上总共需要的就是2*rowNum-2个。
我们可以把这一次的上下看做一个循环,我们考虑一个循环在二维数组的空间占用
我们假设这个数组的长度是length:
int length = s.length();
numRows个横列:
int numOfRec = 2*numRows-2;
竖列的占用我们可以考虑是从numRows递减到0的一个forLoop,总的竖列我们主要考虑循环了多少次就可以了:
int numCols = (length+numOfRec-1)/numOfRec*(numRows-1);
然后我们需要做的就是遍历加入二维数组就行了:
//先往下填写numRows个字符,然后自左下到右上填写
public static String convert(String s, int numRows) {
int length = s.length();
if (numRows==1 || numRows>=length){
return s;
}
// 一循环所需要的字符数
int numOfRec = 2*numRows-2;
//列数
int numCols = (length+numOfRec-1)/numOfRec*(numRows-1);
//创建二维数组
char[][] cars = new char[numRows][numCols];
//遍历插入二维数组
for (int i = 0, x = 0, y = 0; i < length ; ++i) {
cars[x][y]=s.charAt(i);
if (i%numOfRec<numRows-1){
++x;
}else{
--x;
++y;
}
}
//遍历输出
StringBuilder res = new StringBuilder();
for (int j = 0; j < numRows; j++) {
for (int i = 0; i < numCols; i++) {
char c = cars[j][i];
if (c!='\u0000'){
res.append(c);
}
}
}
return res.toString();
}
这道题直观上来说就是二维数组+循环的使用问题,解题方法有一些暴力。需要考虑的难点就是二维数组的双重for循环会导致超时,在此程度上应该有所化简。
结果虽然过了但是不是很满意,以后有机会再优化吧