Divide by Three
来源:互联网 发布:java 反射 实例化单例 编辑:程序博客网 时间:2024/06/14 12:21
A positive integer number n is written on a blackboard. It consists of not more than105 digits. You have to transform it into abeautiful number by erasing some of the digits, and you want to erase as few digits as possible.
The number is called beautiful if it consists of at least one digit, doesn't have leading zeroes and is a multiple of3. For example, 0,99, 10110 are beautiful numbers, and00, 03,122 are not.
Write a program which for the given n will find a beautiful number such thatn can be transformed into this number by erasing as few digits as possible. You can erase an arbitraty set of digits. For example, they don't have to go one after another in the numbern.
If it's impossible to obtain a beautiful number, print -1. If there are multiple answers, print any of them.
The first line of input contains n — a positive integer number without leading zeroes (1 ≤ n < 10100000).
Print one number — any beautiful number obtained by erasing as few as possible digits. If there is no answer, print - 1.
1033
33
10
0
11
-1
In the first example it is enough to erase only the first digit to obtain a multiple of3. But if we erase the first digit, then we obtain a number with a leading zero. So the minimum number of digits to be erased is two.
题意:一个没有前导0的数字中,删若干个数字使它能够被3整除,要求最长的输出
思路:
第一步:求所有数字的和模3,取余数
第二步:从后往前每个数字查询,分为两种,删去余数与第一步余数相同的数字,删去两个余数与第一步不同的数字(不考虑0,1的时候删2,2的时候删1)。
由于从后往前查询,所以得到的一定是最优解,如果删去数字时产生了前导0,即删去了的一位,则证明第一位必须要删去,否则无法得到被3整除的数字。
#include<iostream>#include<stdio.h>#include<algorithm>#include<math.h>#include<string.h>#define maxn 100010using namespace std;int n[maxn];char str[maxn];char ans1[maxn];//第一种方案char ans2[maxn];//第二种方案int main(){ gets(str); int len=strlen(str); int p1=0,p2=0,p3=0,sum=0,mod; //p1表示余数相同的第一个数字 , p2,p3表示余数不同的两个数字 for(int i=1;i<=len;i++){ n[i]=str[i-1]-48; sum+=n[i]; } mod=sum%3; if(mod==0){ //已经是3的倍数的情况 printf("%s",str); return 0; } for(int i=len;i>=1;i--){ if(n[i]%3==mod){ p1=i; break; } } for(int i=len;i>=1;i--){ if(n[i]%3==3-mod){ p3=i; for(int j=i-1;j>=1;j--){ if(n[j]%3==3-mod){ p2=j; break; } } break; } } if(p1!=0){ for(int i=1;i<p1;i++) ans1[i]=n[i]+48; for(int i=p1;i<len;i++) ans1[i]=n[i+1]+48; } if(p2!=0){ for(int i=1;i<p2;i++) ans2[i]=n[i]+48; for(int i=p2;i<p3-1;i++) ans2[i]=n[i+1]+48; for(int i=p3-1;i<len-1;i++) ans2[i]=n[i+2]+48; } int len1=len-1,len2=len-2,st1=1,st2=1,flag1=0,flag2=0;//验证删去数字之后字符串是不是空串 if(ans1[1]=='\0') flag1=1; if(ans2[1]=='\0') flag2=1; if(p1!=0){ while(ans1[st1]=='0'){ st1++; len1--; if(st1==len-1){ len1=0; break; } } } else{ len1=0; } if(p2!=0){ while(ans2[st2]=='0'){ st2++; len2--; if(st2==len-2){ len2=0; break; } } } else{ len2=0; } if(flag1 && flag2) //删去数字后,字符串是空串的情况 printf("-1"); else if(len1==0 && len2 ==0) //删去数字后,字符串只有0的情况 printf("0"); if(len1>=len2) for(int i=0;i<len1;i++) printf("%c",ans1[st1+i]); else for(int i=0;i<len2;i++) printf("%c",ans2[st2+i]); return 0;}
- Divide by Three codeforces
- Divide by Three
- Divide by Three
- codeforces 792C Divide by Three
- CF 792C Divide by Three DP,记忆化搜索
- Educational Codeforces Round 18 C. Divide by Three
- IDL divide by zero
- woj-Divide by Six
- Divide by Six
- WOJ 24. Divide by Six
- Last Digit By Factorial Divide
- divide an array by the size
- woj Divide by Six 数位dp
- woj~24. Divide by Six(dp)
- Divide
- Divide a number by 3 without using *, /, +, -, % operators
- [Integer divide-by-zero] idiv eax,dword ptr []
- some math problems solved by Recursion & divide and conquer
- JDBC
- GDOI2017总结
- Binary Tree
- make 参数详解
- spark-streaming-[5]-Design Patterns for using foreachRDD
- Divide by Three
- HDU 1003
- Python字符串的encode与decode研究心得——解决乱码问题
- JVM虚拟机机制理解
- WCF教程一之WCF是什么,能做什么
- Mosquitto配置----日志设置
- nyoj-喷水装置(一)
- tmk射气球
- Unit2.6 文档