P1553 数字反转(升级版)

题目描述

给定一个数,请将该数各个位上数字反转得到一个新数。

这次与NOIp2011普及组第一题不同的是:这个数可以是小数,分数,百分数,整数。整数反转是将所有数位对调;小数反转是把整数部分的数反转,再将小数部分的数反转,不交换整数部分与小数部分;分数反转是把分母的数反转,再把分子的数反转,不交换分子与分母;百分数的分子一定是整数,百分数只改变数字部分。整数新数也应满足整数的常见形式,即除非给定的原数为零,否则反转后得到的新数的最高位数字不应为零;小数新数的末尾不为0(除非小数部分除了0没有别的数,那么只保留1个0);分数不约分,分子和分母都不是小数(约分滴童鞋抱歉了,不能过哦。输入数据保证分母不为0),本次没有负数。

输入格式

一个数s

输出格式

一个数,即s的反转数

输入输出样例

输入 #1复制
5087462
输出 #1复制
2647805
输入 #2复制
600.084
输出 #2复制
6.48
输入 #3复制
700/27
输出 #3复制
7/72
输入 #4复制
8670%
输出 #4复制
768%

说明/提示

所有数据:25%s是整数,不大于20位

25%s是小数,整数部分和小数部分均不大于10位

25%s是分数,分子和分母均不大于10位

25%s是百分数,分子不大于19位

(20个数据)

 

首先,我们看到这个题,易分析出这个题有四个步骤:拆分,翻转,去零,输出。

所以我们只要分开编出几个函数进行这几个操作即可。

经过观察,易发现:小数的小数部分需要去除的是后部的零,而其他的需要去除的是前部的零。

不多说了,直接上程序:(用的是对字符串的处理)(程序有点长,但思路非常简单易懂)

 

  1 #include
  2 #include  
  3 using namespace std;
  4 string qutou(string a)//作用:去除头部的零
  5 {
  6     int len;
  7     while(a[0]=='0'&&len!=1)//如果第一位还是零
  8     {
  9         len=a.size();
 10         a=a.substr(1,len-1);//把除了第一位之外的部分向前移动一位,覆盖第一位的零
 11     }
 12     return a;
 13 }
 14 string quwei(string a)//作用:去除头部的零
 15 {
 16     int len=a.size();
 17     while(a[len-1]=='0')//如果第一位还是零
 18     {
 19         a=a.substr(0,len-1 );//把除了最后一位之外的部分向后移动一位,覆盖最后一位的零
 20         len--;
 21     }
 22     return a;
 23 }
 24 string fanzhuan(string a)//作用:将数翻转
 25 {
 26     int len=a.size();
 27     string b;//创建一个临时字符串"b"
 28     for(int i=len-1;i>=0;i--)//将a反向粘贴到b上
 29     {
 30         b+=a[i];
 31     }
 32     return b;//返回b
 33 }
 34 int main()
 35 {
 36     string front,behind,total;//字符串front,behind分别用来储存小数和分数的前半部分和后半部分
 37     getline(cin,total);
 38     int len=total.size(),n=0,form=0;
 39     for(int i=0;;i++)//遍历字符串
 40     {
 41         if(total[i]!='/'&&total[i]!='%'&&total[i]!='.')//如果当前位置不是特殊字符
 42         {
 43             front+=total[i];//将这个字符储存进front中
 44         }
 45         if(total[i]=='/')//如果是'/',说明分子已经读入结束
 46         {
 47             form=1;//记录下这个数是分数
 48             n=i+1;
 49             break;//结束读取分子
 50         }
 51         if(total[i]=='%')//如果是'%',说明百分数已经读入结束
 52         {
 53             form=2;//记录下这个数是百分数
 54             break;//结束读取
 55         }
 56         if(total[i]=='.')//如果是'.',说明整数部分已经读入结束
 57         {
 58             form=3;//记录下这个数是小数
 59             n=i+1;
 60             break;//结束读取整数部分
 61         }
 62         if(i==len-1)//如果一直读取到了最后一位还没有特殊符号
 63         {
 64             form=4;//记录下这个数是整数
 65             break;//结束读取
 66         }
 67     }
 68     if(form==1||form==3)//如果是分数或小数
 69     {
 70         for(int j=n;j<=len-1;j++)//读取分母(或小数部分)
 71         {
 72             behind+=total[j];
 73         }
 74         behind=fanzhuan(behind);//翻转后部
 75     }
 76     front=fanzhuan(front);//翻转前部
 77     front=qutou(front);//对前部进行去除头部的零
 78     if(form==1)//如果是分数
 79     {
 80         behind=qutou(behind);//对后部进行去除头部的零
 81         if(front=="\0")//如果前部去头之后什么也不剩,说明前部是零
 82         {
 83             cout<<"0/"<<behind;
 84         }
 85         else
 86         {
 87             cout<"/"<//输出
 88         }
 89     }
 90     if(form==2)//如果是百分数
 91     {
 92         front=qutou(front);
 93         if(front=="\0")//如果前部去头之后什么也不剩,说明前部是零
 94         {
 95             cout<<"0%";
 96         }
 97         else
 98         {
 99             cout<"%";//输出
100         }
101     }
102     if(form==3)//如果是分数
103     {
104         behind=quwei(behind);//对后部进行去除尾部的零
105         if(behind=="\0")
106         {
107             if(front=="\0")//如果前部去头之后什么也不剩,说明前部是零
108             {
109                 front="0";
110             }
111             cout<".0";
112         }
113         else
114         {
115             cout<"."<//输出
116         }
117     }
118     if(form==4)//如果是整数
119     {
120         front=qutou(front);
121         if(front=="\0")//如果前部去头之后什么也不剩,说明前部是零
122         {
123             cout<<"0";
124         }
125         else
126         {
127             cout<//输出
128         }
129     }
130     return 0;
131 }

 

你可能感兴趣的:(P1553 数字反转(升级版))