0
点赞
收藏
分享

微信扫一扫

算法练习-day7

字符串

344. 反转字符串

题意:编写一个函数,其作用是将输入的字符串反转过来。输入字符串以字符数组 s 的形式给出。

注意:不要给另外的数组分配额外的空间,你必须原地修改输入数组、使用 O(1) 的额外空间解决这一问题。

示例:

算法练习-day7_i++

       思路:本题由于是数组存储,因此能想到最简单的就是swap交换两个元素,代码也非常简洁

C++代码:

    void reverseString(vector<char>& s) {
        for(int i=0,j=s.size()-1;i<=j;i++,j--)
        {
            swap(s[i],s[j]);
        }
    }

541. 反转字符串 II

题意:给定一个字符串 s 和一个整数 k,从字符串开头算起,每计数至 2k 个字符,就反转这 2k 字符中的前 k 个字符。

  1. 如果剩余字符少于 k 个,则将剩余字符全部反转。
  2. 如果剩余字符小于 2k 但大于或等于 k 个,则反转前 k 个字符,其余字符保持原样。

示例:

算法练习-day7_i++_02

       思路:本题的思路,大致就是找出2k的起始位置,然后再锁定终止位置2k+k,找到这个区间,然后对该区间的元素进行反转reverse即可。这里我们要注意越界的问题:当右区间大于数组长度时,只反转2*k到字符串末尾的区间即可。

C++代码如下:

    int min(int a,int b)//由于leetcode并没有给出mid,需要自定义
    {
        return a>b?b:a;
    }
    string reverseStr(string s, int k) {
        for(int i=0;i<s.size();i+=(k*2))
        {
            int mid=min(s.size(),i+k);//这里需要做越界处理,若要交换的元素越界了,就会只交换到最末尾
            reverse(s.begin()+i,s.begin()+mid);//反转这个区域内的所有元素
        }
        return s;
    }

05. 替换空格

题意:请实现一个函数,把字符串s中的每个空格替换成"%20"。

示例:

算法练习-day7_字符串_03

       思路:本题的思路蛮简单的,就是使用STL库中自带的replace函数,当我们发现空格时,将空格替换成%20。这里我们需要注意replace是将字符替换为string类型的变量,因此,替换的%20需要“ ”引起来,不能使用单引号

C++代码:

    string replaceSpace(string s) {
        for (int i = 0; i<s.size(); i++)
        {
            if (s[i] == ' ')
            {
                s.replace(s.begin() + i, s.begin() + i + 1, "%20");//直接将空格替换成%20
            }
        }
        return s;
    }

151. 反转字符串中的单词

题意:给你一个字符串 s ,请你反转字符串中 单词 的顺序。单词 是由非空格字符组成的字符串。s 中使用至少一个空格将字符串中的单词分隔开。返回单词顺序颠倒且单词之间用单个空格连接的结果字符串。

注意

  1. 输入字符串 s中可能会存在前导空格、尾随空格或者单词间的多个空格。
  2. 返回的结果字符串中,单词间应当仅用单个空格分隔,且不包含任何额外的空格。

示例:

算法练习-day7_反转字符串_04

       思路:本题我们的思路是,将字符串整个反转,然后对单个单词进行反转。需要注意的是:

  1. 需要去除字符串开头和结尾的多余空格
  2. 需要去除字符串中,单词与单词之间的多余空格

       基于以上注意事项,我选择重新定义一个返回字符串tmp,然后对单个单词进行截取并加入tmp中,其次我们需要注意跳出循环的tmp后会多一个空格,需要去除

C++代码:

    string reverseWords(string s) {
        string tmp;
        reverse(s.begin(), s.end());
        for (int i = 0; i<s.size(); i++)
        {
            while (i<s.size() && s[i] == ' ')//这里会去除开头的空格和跳过中间多余的空格
            {
                i++;
            }
            int j = 0;
            while (j+i < s.size() && s[j+i] != ' ')//j代表单个单词组成字母的个数
            {
                j++;
            }
            string t = s.substr(i, j);//截取该字母
            reverse(t.begin(), t.end());
            t += ' ';
            tmp += t;//写入最终要输出的字符串
            i += j;//继续寻找下一个单词
            t.clear();
        }
        reverse(tmp.begin(),tmp.end());//下面是为了去除最后多添加的空格
        int i=0;
        while(tmp[i]==' ')
        {
            i++;
        }
        tmp=tmp.substr(i);
        reverse(tmp.begin(),tmp.end());
        return tmp;
    }

58 - II. 左旋转字符串

题意:字符串的左旋转操作是把字符串前面的若干个字符转移到字符串的尾部。请定义一个函数实现字符串左旋转操作的功能。比如,输入字符串"abcdefg"和数字2,该函数将返回左旋转两位得到的结果"cdefgab"。

示例:

算法练习-day7_i++_05

       思路:本题还是比较简单的,有两种思路:1.先将n除到s.size()的范围内,然后对s进行二倍复制,然后直接通substr截取以n为开头s.size()长度的字符串即可;2.将s看成两部分,left和right,left就是旋转后的左半部分,即原s的以n为分界线的右半部分,right就是s以开始到n区间的字符,将两个结合,即可返回最终答案

方法1代码:

    string reverseLeftWords(string s, int n) {
        n%=s.size();//假设n过大,其实就是将s转了几圈,n%s.size()后,n就是s的真实改动状态
        int len=s.size();//必须给定原长度,否则后面截取会出现问题
        s+=s;
        return s.substr(n,len);
    }

方法2代码:

    string reverseLeftWords(string s, int n) {
        n%=s.size();//假设n过大,其实就是将s转了几圈,n%s.size()后,n就是s的真实改动状态
        return s.substr(n)+s.substr(0,n);
    }

举报

相关推荐

0 条评论