SDUT 3322 (收索+打表)
2015-09-17 19:26
411 查看
题目描述
一下迭代序列定义在整数集合上:n = n/2 (n 是偶数)
n = n*3 + 1(n 是奇数)
应用以上规则,并且以数字13开始我们得到一下序列:
13,40,20,10,5,16,8,4,2,1
可以看出这个以13开始以1结束的序列一共经过了9次运算。虽然还没有被证明(Collatz问题),但是人们认为在这个规则下,以任何数字开始都会以1 结束。
以哪个不超过x的正整数开始,能得到运算次数最多的序列?
注意:一旦序列开始,也就是从第二项开始,项是可以超过x的。
输入
输了一个整数n,接下来n行,每行一个整数x (1 <=x<=1,000,000)。输出
对于每次询问,你需要计算出最多的运算次数是多少。为了节约输出时间,你只需要输出所有询问的答案之和 。示例输入
3 1 2 3
示例输出
8
看到此题的优化方式首先反应的是打表,但是打表仍然不够
思路: 边打表边收索.是为了减枝,并找到当前步数的最大值.
#include<iostream> #include<algorithm> #include<cstdio> #include<cstring> #include<cmath> #include<math.h> #define ll long long #define MAX 1000010 using namespace std; ll dp[1000010],a[1000010]; inline void read(int& x) { char ch; while (!((((ch=getchar())>='0') && (ch <= '9')) || (ch == '-'))); x = ch-'0'; while (((ch=getchar())>='0') && (ch <= '9')) x = x*10+ch-'0'; } ll DFS(ll i) { if(i==1) { return 0; } if(i<1000000) { if(a[i]) return a[i]; } if((i&1)==0) { return DFS(i/2)+1; } if((i&1)==1) { return DFS(3*i+1)+1; } } int main() { int n,k; ll ma=0,m; for(int i=1;i<=1000000;i++) { a[i]=DFS(i); if(ma<a[i]) ma=a[i]; dp[i]=ma; } read(k); ll ans=0; while(k--) { read(n); ans+=dp ; } printf("%lld\n",ans); return 0; }
相关文章推荐
- const
- 《ACM训练参照》<转载>
- CentOS 7 U盘安装解决找不到U盘问题
- javaweb7
- Unity3D修改FBX文件动画名
- javaweb6
- NetBeans IDE中实现页面跳转的 LoginFrame类
- javaweb3
- HTML5 重力感应 事件讲解
- Spring xml注入实例
- 蓝懿iOS培训日志15 tableView和自定义Cell(1)
- Java多线程基础(一)
- 获取标签的src属性兼容性
- android异步加载AsyncTask
- javaweb2
- 【线性表项目2 - “顺序表”算法库终极完整版】
- Oracle数据库中to_char()函数和to_date()函数的用法
- 使用commons-beanutils把javabean转换成Map日期date不能自定义格式
- cin.get(),cin.getline(),getline()区别
- [cernRoot] How make a beautiful graph by CernRoot?