1.题目


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 R

And 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 s, int numRows);

Example 1:

Input: s = "PAYPALISHIRING", numRows = 3
Output: "PAHNAPLSIIGYIR"

Example 2:

Input: s = "PAYPALISHIRING", numRows = 4
Output: "PINALSIGYAHRPI"
Explanation: P I N
A L S I G
Y A H R
P I

题目大意是要求将一个给定字符串转换为之字形字符串,示意图如下:

2.思路


读完题后第一想法是,找出一种映射关系使得原字符串的下标能够映射为之字形的二维坐标,以题目中给的字符串"PAYPALISHIRING"为例,假定numRows为4,则该二维数组最多4行(若字符串长度小于numRows则不足4行,只有strlen(s)行),但如果这么做,将会浪费大量的空间,而且最终要求返回的字符串长度与输入字符串的长度是相等的,应该存在更简单的做法.

仔细观察变换后的之字形字符串,对于水平方向第一行和最后一行的元素来说,实际上就是原字符串中间距为STEP的元素,其中STEP=2*(numRows-1).还是以"PAYPALISHIRING"为例,设numRows为4,则第一行的元素是:

S[0]='P',S[6]='I',S[12]='N';

最后一行的元素是:

S[3]='P',S[9]='I';

但对于中间的行来说,两个元素间的间距是变化的,所幸这种变化也有规律可循,那就是两次连续的间距之和等于STEP,这样如果我们知道起始两个元素的间距,后面所有元素的间距都能计算出来.从示意图中容易发现,行号越小则起始两元素的间距越大,可以猜测间距应该是一个跟行号相关的变量,实际上行号每加1,间距就减少2,间距减少到0的时候则回绕为STEP.(设第一行起始两个元素的下标为begin,end,对于本例来说begin=0,end=6,那么第二行的起始两个元素的下标就是begin = begin + 1, end = end - 1,显然间距减少了2).有了这些条件,我们就能将原字符串映射为之字形的字符串,具体做法如下:

  1. 从下标0开始,取出所有间距为STEP的元素;
  2. 从下标1开始,取出间距为N的元素,N是一个变化的值,初始值为4,接着变为2,接着又变为4
  3. ......
  4. 从下标i开始,取出间距N=STEP-2*i的元素,接着取出间距为N=STEP-N的元素,两次连续的间距之和为STEP
  5. 若i等于numRows则循环终止

3.实现


char* convert(char* s, int numRows) {
size_t len, i, j, k, m, step;
char *ret; if (numRows == )
return s; len = strlen(s);
ret = malloc((len + ) * sizeof(char)); k = ; /* 转换后的字符串下标 */
m = * (numRows - );
for (i = ; i < numRows; ++i) {
step = m - * i > ? m - * i : m;
for (j = i; j < len; ) {
ret[k++] = s[j];
j += step;
step = m - step > ? m - step : m;
}
}
ret[len] = ;
return ret;
}

虽然整个算法是两层for循环,但时间复杂度并不是O(n2)而是O(n),因为整个算法保证对原字符串每个字符只处理一次,比较直观的解释是内层循环的步长是跳跃式的.

ZigZag Conversion 之字形转换字符串的更多相关文章

  1. 【LeetCode】6. ZigZag Conversion Z 字形变换

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 公众号:负雪明烛 本文关键词:字形变换,ZigZag,题解,Leetcode, 力扣,P ...

  2. 【LeetCode】ZigZag Conversion(Z 字形变换)

    这道题是LeetCode里的第6道题. 题目要求: 将一个给定字符串根据给定的行数,以从上往下.从左到右进行 Z 字形排列. 比如输入字符串为 "LEETCODEISHIRING" ...

  3. 【LeetCode】6. ZigZag Conversion 锯齿形转换

    题目: 思路: 以图为例:s={'A','B','C','D','E','F','G','H'.....} 1.先不考虑中间元素F.G.H.N...,每一行前后元素在数组中对应下标相差size=2*n ...

  4. 字符串按照Z旋转90度然后上下翻转的字形按行输出字符串--ZigZag Conversion

    The string "PAYPALISHIRING" is written in a zigzag pattern on a given number of rows like ...

  5. Leetcode 6 ZigZag Conversion 字符串处理

    题意:将字符串排成Z字形. PAHNAPLSIIGYIR 如果是5的话,是这样排的 P     I AP   YR H L G N  SI A    I 于是,少年少女们,自己去找规律吧 提示:每个Z ...

  6. LeetCode 6. ZigZag Conversion & 字符串

    ZigZag Conversion 看了三遍题目才懂,都有点怀疑自己是不是够聪明... 就是排成这个样子啦,然后从左往右逐行读取返回. 这题看起来很简单,做起来,应该也很简单. 通过位置计算行数: P ...

  7. LeetCode ZigZag Conversion(将字符串排成z字型)

    class Solution { public: string convert(string s, int nRows) { string a=""; int len=s.leng ...

  8. No.006 ZigZag Conversion

    6. ZigZag Conversion Total Accepted: 98584 Total Submissions: 398018 Difficulty: Easy The string &qu ...

  9. LeetCode--No.006 ZigZag Conversion

    6. ZigZag Conversion Total Accepted: 98584 Total Submissions: 398018 Difficulty: Easy The string &qu ...

随机推荐

  1. LOJ 2548 「JSOI2018」绝地反击 ——二分图匹配+网络流手动退流

    题目:https://loj.ac/problem/2548 如果知道正多边形的顶点,就是二分答案.二分图匹配.于是写了个暴力枚举多边形顶点的,还很愚蠢地把第一个顶点枚举到 2*pi ,其实只要 \( ...

  2. Git 安装和使用教程

    Git 安装和使用教程 git 提交 全部文件 git add .  git add xx命令可以将xx文件添加到暂存区,如果有很多改动可以通过 git add -A .来一次添加所有改变的文件.注意 ...

  3. mat函数

    mat函数可以将目标数据的类型转换为矩阵(matrix) data=[[1,1,0,3,1],[1,0,1,4,3],[1,0,1,2,4],[0,1,1,1,2], [2,0,0,3,0],[1,0 ...

  4. cmake中添加-fPIC编译选项方法

    合并openjpeg/soxr/vidstab/snappy等多个cmake库时,为了解决下述问题: relocation R_X86_64_32 against `.text' can not be ...

  5. python 调用C的DLL案例

    前言: python不能直接调用C++只能调用纯C的DLL 此处案例是python模仿opencv的cv2包,但是用c的DLL调用   import osimport csvimport timeim ...

  6. Scrapy实战篇(七)之爬取爱基金网站基金业绩数据

    本篇我们以scrapy+selelum的方式来爬取爱基金网站(http://fund.10jqka.com.cn/datacenter/jz/)的基金业绩数据. 思路:我们以http://fund.1 ...

  7. 电脑忘记WiFi密码了,但又想知道,该怎么办?

    如何查看电脑已经连过的WiFi的密码? 你有没有遇到这样的情况,电脑之前连过的WiFi,正好手机也想连此WiFi,但是忘记密码了,没有WiFi的手机怎么能叫手机呢?.下面我们来看看如何查看已连接过的W ...

  8. Java spring实现文件下载

    一,实现目的,后台写一个controller,然后前台页面点击文件下载,实现文件下载功能.(文件是存放于服务器的磁盘上的) @RequestMapping("/filesdownloads& ...

  9. CentOS7.5 GlusterFS 分布式文件系统集群环境搭建

    环境准备: 系统版本:CentOS Linux release 7.5.1804 (Core) glusterfs:3.6.9 userspace-rcu-master: 硬件资源: 10.200.2 ...

  10. EXT 获取gird各值

    var cellclick = function (item, td, cellIndex, record, tr, rowIndex, e) { //[ListenerArgument(0, &qu ...