洛谷 P1553 数字反转(升级版) 题解
P1553 数字反转(升级版)
Main Idea:
按题目要求将数字反转,注意小数的小数部分末尾不能有0。
Summary:
1.如果是将小数的后半部分求出来后再清零,一定注意只剩一个零的情况,如0.0。
2.题目数据可能会炸int。
Problem Solving Idea:
1.将数字作为字符串读入,先扫描一遍字符串有无‘.’、‘/’和‘%’,如果有‘.’和‘/’,记下该符号的位置分为两部分还原数字,如果无,直接递推还原数字,在有‘%’的情况下在最后加上‘%’。
2.一次性读完字符串,先递推还原数字,如果遇见符号,则记录符号位置然后跳出,然后看符号类型判断是否进行下半段。
AC代码:(version 1)
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
//char a[11],b[1000000];
int main()
{
ll flag=1,mark_pos=-1,mark_00=-1;
string s;
cin>>s;
ll len_1=s.length();
if(s[len_1-1]=='%') mark_00=len_1;
for(ll i=0;i<len_1;i++){
if(s[i]=='/'||s[i]=='.'){
mark_pos=i;
break;
}
}
if(mark_00==-1&&mark_pos==-1){
ll num=0;
for(ll i=len_1-1;i>=0;i--){
num=10*num+(s[i]-'0');
}
cout<<num;
}
else if(mark_00>0){
ll num=0;
for(ll i=len_1-1-1;i>=0;i--){
num=10*num+(s[i]-'0');
}
cout<<num<<'%';
}
else{
ll num_1=0,num_2=0;
for(ll i=mark_pos-1;i>=0;i--){
num_1=10*num_1+(s[i]-'0');
}
for(ll j=len_1-1;j>mark_pos;j--){
num_2=10*num_2+(s[j]-'0');
}
if(num_2!=0){
while(num_2%10==0){
num_2/=10;
}
}
cout<<num_1<<s[mark_pos]<<num_2;
}
return 0;
}
AC代码(version 2)
#include<bits/stdc++.h>
using namespace std;
int main()
{
string s;
char p=0;//放符号
int cnt=0;
cin>>s;
for(int i=0;i<s.size();i++)
{
if(s[i]>='0'&&s[i]<='9') cnt++;//记录第一个数长度
else //遇到符号,记录,跳出
{
p=s[i];
break;
}
}
int x=cnt;//记下第一个数末后一个的位置,也就是符号的位置,如果是分数或小数就要用
cnt--;
while(s[cnt]=='0'&&cnt>0) cnt--;//去除多余前导0;
for(int i=cnt;i>=0;i--)
cout<<s[i];
if(p==0) return 0;//▲▲▲▲
else
if(p=='%') {cout<<p;return 0;}
else cout<<p;
int m=s.size()-1;
while(s[x+1]=='0'&&x<m-1) x++;
while(s[m]=='0'&&m>x+1) m--;
for(int i=m;i>x;i--)
cout<<s[i];
return 0;
}