6. Z字形变换

一、题目原型:

将字符串 "PAYPALISHIRING" 以Z字形排列成给定的行数:
输入: s = "PAYPALISHIRING", numRows = 3
输出: "PAHNAPLSIIGYIR"
输入: s = "PAYPALISHIRING", numRows = 4
输出: "PINALSIGYAHRPI"
实现一个将字符串进行指定行数变换的函数:
string convert(string s, int numRows);

二、题目意思剖析:

 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

三、解题思路:

3.1. 将原字符串按照“z字转换规律”保存进一个二维数组
3.2.将该二维数组横竖对调,得到最后的二维数组
3.3.用字符串拼接得到最后的答案

核心思路:找规律,找关键的几个数据和numRows、字符串总长度之间的关系。
下图中方框内表示一个单元格。


笔记思路
第一步:能够看出,这个排列是由一个个单元格(相同的排列)组成。
 P      I       N
 A   L  S    I  G
 Y A    H  R
 P      I
其中,单元格是
 P
 A   L
 Y A
 P
第二步:算出每一个单元所包含的字符个数

很简单可以看出,每个单元是由最长的那一列+中间的那几个字符。
而中间那些字符,刚好是除去最上面和最下面的那些。
所以:

let letterCount = numRows + (numRows - 2)
第三步:每个单元格包含的列数

1表示是行数最大那一列,(numRows - 2)是中间过渡的那几列

let cols: Int = 1 + (numRows - 2)
第四步:总共有多少个单元格
var count: Int = 0
while letterCount*count <= letters.count {
    
    count = count + 1
}
// 因为最后count会再次累加1,所以需要减1.
count = count - 1
第五步:总共列数
// 最终列数
var allCols: Int = 0
// 余数:比如字符长度为17,17 % 6 = 5
let remainder = letters.count % letterCount
if remainder == 0 { // 说明刚好有整数个单元格
    allCols = count * cols
}else if remainder >= numRows && remainder < letterCount { 
    //如果余数大于或者行数,并且小于一个单元格所包含的最大字符数,allCols = 前面整数个的单元格列数 + 1 + (余数 - numRows)
    allCols = count * cols + 1 + (remainder - numRows)
}else {
    // 比如上面的例子, PAYPALISHIRING中,结果余数 = 14%6 = 2,2 < numRows,所以allCols =  前面整数个的单元格列数 + 1
    allCols = count * cols + 1
}
// 1.前二维数组
var allConvert = dim(allCols, dim(numRows, "*"))
var index: Int = 0 // 总字符串索引
for i in 0..<allCols {
    // i % cols,余数 - 指的是字母离底部多长。
    if i % cols == 0 { // 当余数为0时,就是最长列的时候。
        var convert: [String] = Array.init(repeating: "*", count: numRows)
        var j: Int = 0
        while index < letterCount * (i/cols + 1) && index < letters.count && j < numRows {
            convert[j] = letters[index]
            allConvert[i] = convert
            index = index + 1
            j = j + 1
        }
    }else { // 其他时候,就是用( 最大行数 - 1 - 余数 )
        var convert: [String] = Array.init(repeating: "*", count: numRows)
        convert[numRows - 1 - i%cols] = letters[index]
        allConvert[i] = convert
        index = index + 1
    }
}
print(allConvert)

这里需要一个创建二维数组的函数

// 创建二维数组
func dim<T>(_ count: Int, _ value: T) -> [T] {
    return [T](repeating: value, count: count)
}
第六步:横竖置换
[["a", "b", "c", "d"],
 ["*", "*", "e", "*"],
 ["*", "f", "*", "*"],
 ["g", "h", "i", "j"],
 ["*", "*", "k", "*"],
 ["*", "l", "*", "*"]]
         变成
 [["a", "*", "*", "g", "*", "*"],
 ["b", "*", "f", "h", "*", "l"],
 ["c", "e", "*", "i", "k", "*"],
 ["d", "*", "*", "j", "*", "*"]]
// 将数组横转,横 -> 竖
// i[0,6) j[0,4)  ->   i[0,4) j[0,6)
var resultConverts = dim(numRows, dim(allCols, "*"))
for i in 0..<allCols {
    for j in 0..<numRows {
        resultConverts[j][i] = allConvert[i][j]
    }
}
第七步:拼接最终字符串
var result: String = ""
for i in 0..<numRows {
    for j in 0..<allCols {
        if resultConverts[i][j] != "*" {
            result.append(resultConverts[i][j])
        }
    }
}
print(resultConverts)
// result就是我们需要的答案

四、小结

总提交数
提交结果

思路完全正确的,就是耗时太长了,

有其他好的方法请极速留言,非常乐意一起探讨。😄
个人博客地址

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,185评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,445评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,684评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,564评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,681评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,874评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,025评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,761评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,217评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,545评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,694评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,351评论 4 332
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,988评论 3 315
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,778评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,007评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,427评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,580评论 2 349

推荐阅读更多精彩内容

  • 1、通过CocoaPods安装项目名称项目信息 AFNetworking网络请求组件 FMDB本地数据库组件 SD...
    阳明先生_X自主阅读 15,969评论 3 119
  • 一、Java 简介 Java是由Sun Microsystems公司于1995年5月推出的Java面向对象程序设计...
    子非鱼_t_阅读 4,160评论 1 44
  • 在C语言中,五种基本数据类型存储空间长度的排列顺序是: A)char B)char=int<=float C)ch...
    夏天再来阅读 3,339评论 0 2
  • 官网 中文版本 好的网站 Content-type: text/htmlBASH Section: User ...
    不排版阅读 4,374评论 0 5
  • 今天很开心我加盟的事情终于着手开始了,而且刚好是朝着自己理想的方向在发展。感恩种子! 我近期的目标是财富,我希望今...
    belivePossible阅读 55评论 0 2