原题:埃森哲杯第十六届上海大学程序设计联赛春季赛暨上海高校金马五校赛 I
题意:
给出一个十进制数,输出和这个数最近的一个二数(所有位都是偶数0,2。。。)
解析:
最近的有两种可能,往上和往下
假设有数241837152831
往上的第一个二数,应该是把最高位的一个奇数++,后面的全部变成0,即242000000000
往下的,则是第一个奇数–,后面的变成8,即240888888888,然后判断这两个和原来的数哪个差比较小即可
注意点:
- 往上时,对于处理出来的string,从后往前判断一遍,如果有位置大于9(ASC码),
x[i]-=10,x[i-1]+=2
- 在输入原来的数后,要在前面加上一个0,即
x="0"+x
,因为如果第一位有进位时需要 - 输出时去掉前缀0
代码:
#include<bits/stdc++.h>
using namespace std;
#define N 50009
#define D long long
string x;
string sub(string a,string b){//a>b
string ans=x;
for(int i=ans.length()-1;i>=0;i--){
if(a[i]>=b[i])ans[i]='0'+a[i]-b[i];
else{
a[i-1]--;a[i]+=10;
ans[i]='0'+a[i]-b[i];
}
}
return ans;
}
void out(string x){
int ar=0;
for(;ar<x.length()-1;ar++){
if(x[ar]!='0')break;
}
cout<<x.substr(ar)<<endl;
}
int main(){
int t;cin>>t;while(t--){
cin>>x;x="0"+x;
string b=x,s=x;
for(int i=0;i<b.length();i++){
if((b[i]-'0')%2==0)continue;
b[i]++;
for(int j=i+1;j<b.length();j++)b[j]='0';
for(int j=i;j>=0;j--){
if(b[j]>'9')b[j]='0',b[j-1]+=2;
}
break;
}
for(int i=0;i<s.length();i++){
if((s[i]-'0')%2==0)continue;
s[i]--;
for(int j=i+1;j<s.length();j++)s[j]='8';
break;
}
string subs=sub(x,s),subb=sub(b,x);
if(subs<=subb)out(s);
else out(b);
}
}