String Compression

需求:

给定一个字符数组chars,由若干个字符组成,现对其进行简化,比如"aaabbcc",将其转化成"a3b2c2"

,如果字符个数是1,那么不需要进行简化。要求in-place,即直接修改原始字符数组。

分析:

1)特殊情况处理:如果字符数组是null,那么抛出参数异常;如果字符数组长度是0或者1,那么无需进行简化,直接返回数组长度即可。

2)定义三个变量,字符变量ch,存储出现的字符,整型变量num,存储每个字符的出现次数,整型变量index,维护更新后字符数组的长度。ch初始化为第一个字符,num初始化为1,index初始化为0。从第二个字符开始遍历字符数组,如果当前字符和ch相同,那么num++,如果不同,说明已经求完上一个片段的字符个数,更新字符数组,chars[index++] = ch

,判断num是否为1,如果不为1,那么需要将num转成字符串,依次添加到chars数组中,然后更新ch为当前字符,num更新为1,循环此过程。

3)对于最后一个字符段,和过程2)相似,更新chars[index++] = ch

,如果出现次数num不是1,那么需要将其转成字符串,添加到chars中,如果次数num是1,那么不需要更新chars数组。

4)新的数组长度一定小于等于原始的数组长度。因为如果原始字符数组中字符出现次数是1,那么不需要简化修改,如果是2,比如"aa",那么简化之后是"a2",更新之后的数组和原始数组长度相同,如果次数大于2,那么更新之后的长度一定是小于原始长度的,所以index一定小于等于遍历的角标,不会出现覆盖还未被遍历的字符的情况。

时间复杂度:O(N)。

空间复杂度:O(1)

代码:

class Solution {
    public int compress(char[] chars) {
        //异常处理
        if(chars == null)
            throw new IllegalArgumentException("illegal parameters");
        
        //如果chars长度是0或者1,那么不需要进行简化,直接返回其长度
        if(chars.length == 0 || chars.length == 1)
            return chars.length;
        
        //定义三个变量
        //char ch: 存储当前字符段对应的字符
        //int num: 存储当前字符段字符ch出现的次数
        //int index: 维护有效的数组长度
        char ch = chars[0];
        int num = 1;
        int index = 0;
        
        for(int i = 1; i < chars.length; i++){
            if(chars[i] == ch)
                num++;
            else{
                //说明先前的字符段已经遍历完,需要更新字符数组
                chars[index++] = ch;
                if(num > 1){
                    String s = num+"";
                    
                    for(int j = 0; j < s.length(); j++)
                        chars[index++] = s.charAt(j);
                }
                
                //更新ch和num
                ch = chars[i];
                num = 1;
            }
        }
        
        //对最后一个字符段进行单独处理
        chars[index++] = ch;
        if(num > 1){
            String s = num+"";
            
            for(int i = 0; i < s.length(); i++)
                chars[index++] = s.charAt(i);
        }
        
        return index;
    }
}


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值