题目来源是隔壁班级老师c++实验课的题目,看着蛮变态的,比笔者班级的实验题难的不是一点半点,那么具体怎么实现呢
核心的思路来源与以前写过的连续几个连续输入的整型数,每种数字一共连续出现过几次,看看它的代码长什么样
int currval=0,val=0; if(std::cin>>currval) { int cnt=1; while(std::cin>>val) { if(val==currval) ++cnt; else { std::cout<<currval<<" occurs "<<cnt<<" times"<<std::endl; currval=val; cnt=1; } } std::cout<<currval<<" occurs "<<cnt<<" times"<<std::endl; }
这个代码很简单,笔者就不加注释了,那么解压缩数组的题目要求和这道题有极其相似的地方,都是连续的数字,都要输出连续出现了几次,只不过要求把单独出现的数字特殊化处理以及提供解压的函数,实际上本质是没有太大改变的。那么怎么对单独出现的数字特殊化处理呢,笔者采用的方法是:遇到单独出现的数字,在压缩结果的这个数组中(以下简称result),相应的位置用-1代替,然后把这个数字存到另外一个单独存放这种单一数字的数组中去(以下简称single_result),可能文字描述有些难以理解,那么看看按照这种方式压缩后两个数组分别长什么样吧

如图,第一行和第二行是原始的数组,即a[100],result是主要的压缩后的数据,single_result是存放单个数字的压缩后数据
a[100]的前三个是连续的3个1,那么result相应的结果就是“3,1”,然后是3个3,result相应的结果就是“3,3”,然后是“4,5,6”,这3个单独的数字,那么在result中用-1代替,就是“-1,-1,-1”,然后把他们存在single_result中。
这就是压缩的原理,那么看看代码是怎么实现的
void compress(int a[100],vector<int> &result,vector<int> &single_result){ int currval=0,val=0; if(currval=a[0]){ int cnt=1; for(int i=1;i<100;i++){ val=a[i]; if(val==currval) ++cnt;//如果和上次的数据一样,计数值加一 else{//如果不一样,将压缩后的数据放入result或single_result中 if(cnt!=1){//计数值不为1,将计数值和数字压入result的末尾 result.push_back(cnt); result.push_back(currval); } else{//计数值为1,将将-1压入result末尾,将数字压入single_result result.push_back(-1); single_result.push_back(currval); } currval=val; cnt=1; } } if(cnt!=1){//同上 result.push_back(cnt); result.push_back(currval); } else{//同上 result.push_back(-1); single_result.push_back(currval); } } }
大体的结构和原来一样,只是加了相关的vector操作
那么解压的函数如何实现呢,实际上了有了压缩后的结构,解压就很简单了,直接贴代码,具体原理应该都看得懂
void decompress(vector<int> &result,vector<int> &single_result){ vector<int> final; for(int i=0,j=0;i<result.size();){ if(result[i]!=-1){ for(int k=0;k<result[i];k++){ final.push_back(result[i+1]); } i+=2; } else{ final.push_back(single_result[j]); j++; i++; } } for(auto a:final){ cout<<a<<","; } cout<<endl; }
贴个结果看看正确性

完 全 一 致
按理说还有改进的方法,笔者能想到的就是把连续 几个单独的数字用一个-1来表示,但是相应的会在single_result中增加一个参数表示连续的单数字出现的数量,本质上压缩大小并未减少,因此未进行代码实现。
以上案例代码没有加上指针,以下是使用指针的完整代码
1 #include<iostream> 2 #include<vector> 3 using namespace std; 4 void compress(int *p,vector<int> *result,vector<int> *single_result){ 5 int currval=0,val=0; 6 if(currval=*p){ 7 int cnt=1; 8 for(int i=1;i<100;i++){ 9 val=*(p+i); 10 if(val==currval) 11 ++cnt; 12 else{ 13 if(cnt!=1){ 14 result->push_back(cnt); 15 result->push_back(currval); 16 } 17 else{ 18 result->push_back(-1); 19 single_result->push_back(currval); 20 } 21 currval=val; 22 cnt=1; 23 } 24 } 25 if(cnt!=1){ 26 result->push_back(cnt); 27 result->push_back(currval); 28 } 29 else{ 30 result->push_back(-1); 31 single_result->push_back(currval); 32 } 33 } 34 } 35 void decompress(vector<int> *result,vector<int> *single_result){ 36 vector<int> final; 37 for(int i=0,j=0;i<result->size();){ 38 if((*result)[i]!=-1){ 39 for(int k=0;k<(*result)[i];k++){ 40 final.push_back((*result)[i+1]); 41 } 42 i+=2; 43 } 44 else{ 45 final.push_back((*single_result)[j]); 46 j++; 47 i++; 48 } 49 } 50 for(auto a:final){ 51 cout<<a<<","; 52 } 53 cout<<endl; 54 } 55 int main(){ 56 int a[100]={1,1,1,3,3,3,4,5,6,5,5,5,5,5,3,3,4,4,7,8,9,1,1,1,3,3,3,3,4,4,5,4,6,5,5,5,5,4,4,4,5,3,3,3,3,4,4,4,4,7,7,7,7,8,9,9,9,9,0,0,0,0,3,3,3,4,5,6,7,3,3,3,5,5,5,8,7,8,8,8,8,3,3,3,4,4,5,5,5,5,4,5,5,4,4,4,4,1,1,1}; 57 vector<int> *result=new vector<int>; 58 vector<int> *single_result=new vector<int>; 59 compress(a,result,single_result); 60 cout<<"After compress:"; 61 for(auto a:*result) cout<<a<<","; 62 cout<<endl; 63 for(auto a:*single_result) cout<<a<<","; 64 cout<<endl; 65 cout<<"Decompress:"; 66 decompress(result,single_result); 67 delete result; 68 delete single_result; 69 system("pause"); 70 return 0; 71 }
ps:隔壁学到这里的时候是没有学到vector的,所以实际上笔者写的有点超纲了,但是数组配指针的组合真的难看,懒得写了(小声逼逼)
浙公网安备 33010602011771号