Easy
Given an array of characters, compress it in-place.
The length after compression must always be smaller than or equal to the original array.
Every element of the array should be a character (not int) of length 1.
After you are done modifying the input array in-place, return the new length of the array.
Example 1:
Input:["a","a","b","b","c","c","c"]Output:Return 6, and the first 6 characters
of the input array should be: ["a","2","b","2","c","3"]Explanation:"aa" is
replaced by "a2". "bb" is replaced by "b2". "ccc" is replaced by "c3".
Example 2:
Input:["a"]Output:Return 1, and the first 1 characters of the input array
should be: ["a"]Explanation:Nothing is replaced.
Example 3:
Input:["a","b","b","b","b","b","b","b","b","b","b","b","b"]Output:Return 4, and
the first 4 characters of the input array should be:
["a","b","1","2"].Explanation:Since the character "a" does not repeat, it is not
compressed. "bbbbbbbbbbbb" is replaced by "b12".Notice each digit has
it's own entry in the array.
Note:
All characters have an ASCII value in [35, 126]
1 <= len(chars) <= 1000
这个题想了很久没想出来,网上有个做法是input为string s的同一道题,我本来想先把char array转换成string直接按着那个方法做,但是这道题要求的是in place解,就是必须直接在原来的array上改动,不能新增array或者转成string去做。
这道题用三个指针,i,j表示的是移动的两个pointers, 用来“包住”相同的字符串的部分;k用来写找index写入char[] chars。比如[a,a,b,b,b,c,c,c,c]这个input. 一开始i = j = k = 0, 然后j会一直右移到j = 2. 这个时候我们用k找到该写入的地方,先是写入a再右移k, char[k++] = char[i]; 然后我们检查是否j – i >= 2,如果是就说明同一个char有重复的,这个时候我们就要把重复的次数写到chars里面去。这里用的技巧比较难想到,先是把j – i这个int转换成string,然后再把string转成char array, 再把每一个array元素写到chars里面去。最后我们将i移动到j的位置,继续while loop. 最后的k刚好落到chars最后一个元素后一个index,就是我们元素的个数。
class Solution {
public int compress(char[] chars) {
int n = chars.length;
int i = 0, j = 0, k = 0;
while (i < n){
while (j < n && chars[i] == chars[j]){
j++;
}
chars[k++] = chars[i];
if (j - i >= 2){
for (char c : String.valueOf(j - i).toCharArray()){
chars[k++] = c;
}
}
i = j;
}
return k;
}
}