[2016/7/9][USACO1.5][dp]Superprime Rib
2016-07-09 19:25
190 查看
题目链接:http://train.usaco.org/usacoprob2?a=gR1up10aYLj&S=sprime
题目大意:让你计算n(n在1,8之间)位的,依次抹去它最后一位数字,每次所得到的数仍然是质数的数字。
一些想法:
开始想先用素数筛选出质数,在其中找满足条件的数字。(完全被上一道题带着思路走了
后来想想太暴力了啊喂!1e8的数组开不起啊喂!
开始仔细想题目,这个时候发现,不就是状态依次叠加吗!从1开始,先列出满足条件的数,再以1为基础,算2位满足条件的。以此类推直至到n。在过程中只需要为前一个状态添加尾数,判断是不是素数就好。
这是一道送分题啊同学们!!不就是记忆化搜索嘛!!
就算用了很小学生的素数判断方法,速度还是很快的。毕竟越到后面虽然数字位数越大,但是其数量却减小了。
于是开vector,造一个哈希表,然后打表就好了!
代码:
/*
ID: 49743541
LANG: C++
TASK: sprime
*/
#include <stdio.h>
#include <math.h>
#include <vector>
using namespace std;
vector<int> list[9];
void init(){
list[1].push_back(2);
list[1].push_back(3);
list[1].push_back(5);
list[1].push_back(7);
}
bool isprime(int num){
int s = sqrt(num);
for(int i = 2; i<=s; i++){
if(!(num%i))
return false;
}
return true;
}
int n;
int a[5] = {1,3,5,7,9};
int main(){
freopen("sprime.in", "r", stdin);
freopen("sprime.out", "w", stdout);
init();
scanf("%d",&n);
int j,k;
int A;
for(int i = 2;i<=n;i++){
for(j = 0;j<list[i-1].size();j++){
A = list[i-1][j]*10;
for(k=0;k<5;k++){
if(isprime(A+a[k]))
list[i].push_back(A+a[k]);
}
}
}
for(int i = 0;i<list
.size();i++)
printf("%d\n",list
[i]);
return 0;
}
题目大意:让你计算n(n在1,8之间)位的,依次抹去它最后一位数字,每次所得到的数仍然是质数的数字。
一些想法:
开始想先用素数筛选出质数,在其中找满足条件的数字。(完全被上一道题带着思路走了
后来想想太暴力了啊喂!1e8的数组开不起啊喂!
开始仔细想题目,这个时候发现,不就是状态依次叠加吗!从1开始,先列出满足条件的数,再以1为基础,算2位满足条件的。以此类推直至到n。在过程中只需要为前一个状态添加尾数,判断是不是素数就好。
这是一道送分题啊同学们!!不就是记忆化搜索嘛!!
就算用了很小学生的素数判断方法,速度还是很快的。毕竟越到后面虽然数字位数越大,但是其数量却减小了。
于是开vector,造一个哈希表,然后打表就好了!
代码:
/*
ID: 49743541
LANG: C++
TASK: sprime
*/
#include <stdio.h>
#include <math.h>
#include <vector>
using namespace std;
vector<int> list[9];
void init(){
list[1].push_back(2);
list[1].push_back(3);
list[1].push_back(5);
list[1].push_back(7);
}
bool isprime(int num){
int s = sqrt(num);
for(int i = 2; i<=s; i++){
if(!(num%i))
return false;
}
return true;
}
int n;
int a[5] = {1,3,5,7,9};
int main(){
freopen("sprime.in", "r", stdin);
freopen("sprime.out", "w", stdout);
init();
scanf("%d",&n);
int j,k;
int A;
for(int i = 2;i<=n;i++){
for(j = 0;j<list[i-1].size();j++){
A = list[i-1][j]*10;
for(k=0;k<5;k++){
if(isprime(A+a[k]))
list[i].push_back(A+a[k]);
}
}
}
for(int i = 0;i<list
.size();i++)
printf("%d\n",list
[i]);
return 0;
}
相关文章推荐
- PHP session 防止重复登录
- easyui datagrid 小结
- 如何在Fedora或CentOS上使用Samba共享
- 九度OJ 1041 简单排序
- andriod 打造炫酷的电影票在线选座控件,1比1还原淘宝电影在线选座功能
- windows下建立以.开头的文件夹
- 图片旋转总结
- 学了这四招,你在Linux上观看Netflix视频不发愁
- 面向对象12
- mysql GROUP BY 代替DISTINCT 遇到的问题及解决
- 面向对象11
- Service的生命周期
- 将jQWidgets图片导入Excel
- NumPy的详细教程
- 面向对象10
- SQLiteDatabase
- JavaScript中Array类型数组的一些方法小结
- 剑指offer之面试题21:包含min函数的栈
- ChainOfResponsibility--责任链模式
- Android中View绘制流程分析