1078 字符串压缩与解压 (20 point(s))
Posted Atl212
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了1078 字符串压缩与解压 (20 point(s))相关的知识,希望对你有一定的参考价值。
地址加来加去搞得有点晕头转向的,而且当时还以为是在控制字符,自增的时候没注意,把迭代器自增了,指向就不对了自然结果就错了。
所以用迭代器 auto 指向地址的时候得注意自增自减的运算,不然很容易把自己搞混,指向错误都不知道,然后调试代码半天。
而看了别人的代码才想到,字符串没有必要用迭代器,直接用数字下标遍历就可以了。不然迭代器还只能 ++ -- 不能做跨越几步的运算,用起来不是很方便。
而用迭代器的时候出现了一个问题,因为压缩的时候要判断字符是否重复,所以用了循环来遍历,直到遇到不同的字符后或者到字符串末尾。
但是当前指向末尾会有问题,因为 for 循环在结束之后会递增一次,导致最后可能就跳出末尾到末尾后面去了,导致无限循环。所以这种写法最后还得判断一次来结束程序。
写的时候没注意条件, “被压缩或解压的不超过 1000 个字符的字符串” ,后面重新花了点时间穷举解压部分数字处理的代码。代价就是用了很多迭代器,看起来有点憨。
而看别人的代码根本不需要这样,用一个循环来判断后续是否是数字就可以了。
i += count;
本来想用迭代器模拟一下别人用下标操作的方式,上面这个还是可以的,可以用这个循环来 ++ 达到同样的效果。虽然有点憨憨。
while(a != b) a++;
if (str[j] == str[j+1])
但是发现这个就无法模拟了,因为迭代器不能做到这种暂时 + 1 的操作,而这个是用来比较前后两个字符是否相同,所以如果有相同字符比如 aaab 那么最后这个 j 会停在 b 前面的 a 上。
但是用迭代器就只能这样写 if(*a == *b) 而这一最后会停在 b 上面,这回导致最后判断的不一样,无法模仿。
while (isdigit(str[i])) count = count * 10 + str[i++] - \'0\';
if (isdigit(s[i])) num += s[i];
还有就是学到了两种读取数字的方式,前面一个是判断是字符串然后加到计数变量中。后面是通过字符串拼接将属于数字的字符拼起来,然后在通过 stoi() 转换为数字。
这比下面的暴力拆解要合理多了。
// 乱糟糟的代码 但却AC的代码
#include <bits/stdc++.h>
using namespace std;
int main() {
string c, str;
cin >> c;
getchar();
getline(cin, str);
if(c == "C"){
for(auto b = ++begin(str); b != end(str); b++){
auto a = --b;
if(*a == *b){
while(*a == *b && b != end(str)){
b++;
}
if(b - a != 1) cout << b - a;
}
cout << *a;
if(b == --end(str)) cout << *b;
if(b == end(str)) return 0;
}
}
else{
for(auto a = begin(str); a != end(str); a++){
if(isdigit(*a)){
int num;
auto b = a; ++b; auto c = b; c++; auto out = c;
if(isdigit(*b) && isdigit(*c)) {
num = (*a - \'0\') * 100 + (*b - \'0\') * 10 + (*c - \'0\');
out = ++c;
}
else if(isdigit(*b)) {
num = (*a - \'0\') * 10 + (*b - \'0\');
out = c;
}
else{
num = (*a - \'0\');
out = b;
}
for(int i = 0; i < num; i++)
cout << *out;
// ++ 会被跳过
a = out;
}
else cout << *a;
}
}
}
以上是关于1078 字符串压缩与解压 (20 point(s))的主要内容,如果未能解决你的问题,请参考以下文章