传送门
解:就是个模拟了,唯一要注意的删除同样的0,删除中间的使得结果更短,因为多删除一个:号。
比赛写的代码就比较臭了。
#include<bits/stdc++.h>
#define il inline
#define pb push_back
#define ms(_data,v) memset(_data,v,sizeof(_data))
#define sc(n) scanf("%d",&n)
#define SC(n,m) scanf("%d %d",&n,&m)
#define SZ(a) int((a).size())
#define rep(i,a,b) for(int i=a;i<=b;++i)
#define drep(i,a,b) for(int i=a;i>=b;--i)
using namespace std;
typedef long long ll;
const ll inf=0x3f3f3f3f;
const double pi=acos(-1.0);
const double eps=1e-9;
void cg(const char *sSrc, char *sDest, int nSrcLen) {
int times=nSrcLen/4;
char temp[times];
int x=0;
for(int i=0; i<times; i++) {
x=8*(sSrc[i*4]-'0');
x+=4*(sSrc[i*4+1]-'0');
x+=2*(sSrc[i*4+2]-'0');
x+=sSrc[i*4+3]-'0';
sprintf(temp+i,"%1x",x);
}
memcpy(sDest,temp,times);
}
char b[500],a[2000];
int T,id=0;
struct node {
int st,num,ls;
};
bool cmp(node x,node y) {
if(x.num!=y.num) return x.num>y.num;
else return x.st>y.st;
}
vector<node> tt;
int main() {
sc(T);
while(T--) {
scanf("%s",a);
cg(a,b,strlen(a));
string ans="";
int cnt=0;
bool fg=0;
for(int i=0; i<32; i+=4) {
fg=0;
for(int j=i; j<i+4; ++j) {
if(b[j]!='0' && !fg) {
fg=1;
ans+=b[j];
}
else if(fg) ans+=b[j];
}
if(!fg) ans+='0',cnt++;
if(i<28)ans+=':';
}
// cout<<ans<<endl;
cout<<"Case #"<<(++id)<<": ";
if(cnt==8) cout<<"::"<<endl;
else {
tt.clear();
int nst=-1,tot=0,ls;
for(int i=0; i<SZ(ans);) {
if(ans[i]=='0' && (i==0 || ans[i-1]==':')) {
if(i==0) nst=i;
else nst=i-1;
tot=0;
int j;
for(j=i; j<SZ(ans); ++j) {
if(ans[j]=='0') tot++;
if(ans[j]!='0' && ans[j]!=':') break;
}
if(tot>=2) tt.pb(node {nst,j-nst,j});
i=j;
}
else ++i;
}
if(SZ(tt)==0) {
cout<<ans<<endl;
}
else {
sort(tt.begin(),tt.end(),cmp);
node tp=tt[0];
//cout<<"erase "<<tp.st<<" "<<tp.ls<<endl;
ans.erase(ans.begin()+tp.st,ans.begin()+tp.ls);
ans.insert(tp.st,"::");
cout<<ans<<endl;
}
}
}
return 0;
}