100-The 3n + 1 problem
题目:
http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=36
1 The 3n + 1 problem
Time limit: 3.000 seconds
2 注意
- 中间的计算结果会大于INT_MAX,所以应该使用long long 来存储n
- 输入的i,j,不一定i < j
3 分析
本体考查的是穷举法+DP,还有能否优化程序提高效率的能力。
4 解法1-[笨法]
4.1 参考
4.2 耗时
0.965s
4.3 分析
直接穷举,不用动脑子
4.4 源码
#include <algorithm>
#include <iostream> using namespace std; int main(int argc, char *argv[])
{
while ()
{
int i, j, _max = ;
cin >> i >> j;
if (cin.fail())
break; int temp_min = min(i, j);
int temp_max = max(i, j); for (int k = temp_min; k <= temp_max; ++k)
{
long long n = k;
int count = ;
while ( != n)
{
count++;
if ( == n % )
n = * n + ;
else
n = n / ;
} _max = max(_max, count);
}
cout << i << " " << j << " " << _max << endl;
} return ;
}
5 解法2-[穷举法+DP]
5.1 参考
http://blog.csdn.net/metaphysis/article/details/6431937
5.2 耗时
0.045s
5.3 分析
- 中间计算结果可以保存下来,供后续计算使用。
- n=3n+1可以优化为n += (n << 1) + 1;
- n=n/2 可以优化为n = n >> 1;
5.4 源码
#include <iostream>
#include <algorithm> #define MAXSIZE 1000000 using namespace std; int cache[MAXSIZE]; int recursion(long long _n); int
main(int argc, char *argv[])
{
int i, j;
while (cin >> i >> j)
{
int result = , _max = ;
const int begin = min(i, j);
const int end = max(i, j);
for (long long k = begin; k <= end; ++k)
{
result = recursion(k);
_max = max(_max, result);
} cout << i << " " << j << " " << _max << endl;
} return ;
}
int
recursion(long long _n)
{
int count = ; if ( == _n)
count = ;
else
{
count++;
if (_n & )
_n += (_n << ) + ;
else
_n = _n >> ; if (MAXSIZE <= _n)
{
// _n is too large to record the result in cache
count += recursion(_n);
}
else
{
// DP, cache the result to speed up
if ( == cache[_n])
{
count += recursion(_n);
cache[_n] = count;
}
else
count = cache[_n];
}
} return count;
}
6 解法3-[穷举法+DP]
6.1 参考
http://blog.csdn.net/metaphysis/article/details/6431937
6.2 耗时
0.052s
6.3 分析
6.4 源码
// The 3n+1 problem (3n+1 问题)
// PC/UVa IDs: 110101/100, Popularity: A, Success rate: low Level: 1
// Verdict: Accepted
// Submission Date: 2011-05-22
// UVa Run Time: 0.032s
//
// 版权所有(C)2011,邱秋。metaphysis # yeah dot net。
//
// [问题描述]
// 考虑如下的序列生成算法:从整数 n 开始,如果 n 是偶数,把它除以 2;如果 n 是奇数,把它乘 3 加
// 1。用新得到的值重复上述步骤,直到 n = 1 时停止。例如,n = 22 时该算法生成的序列是:
//
// 22,11,34,17,52,26,13,40,20,10,5,16,8,4,2,1
//
// 人们猜想(没有得到证明)对于任意整数 n,该算法总能终止于 n = 1。这个猜想对于至少 1 000 000
// 内的整数都是正确的。
//
// 对于给定的 n,该序列的元素(包括 1)个数被称为 n 的循环节长度。在上述例子中,22 的循环节长度
// 为 16。输入两个数 i 和 j,你的任务是计算 i 到 j(包含 i 和 j)之间的整数中,循环节长度的最大
// 值。
//
// [输入]
// 输入每行包含两个整数 i 和 j。所有整数大于 0,小于 1 000 000。
//
// [输出]
// 对于每对整数 i 和 j,按原来的顺序输出 i 和 j,然后输出二者之间的整数中的最大循环节长度。这三
// 个整数应该用单个空格隔开,且在同一行输出。对于读入的每一组数据,在输出中应位于单独的一行。
//
// [样例输入]
// 1 10
// 100 200
// 201 210
// 900 1000
//
// [样例输出]
// 1 10 20
// 100 200 125
// 201 210 89
// 900 1000 174
//
// [解题方法]
// 计算每个数的循环节长度,求给定区间的最大值。
//
// 需要注意:
// 1. 中间计算过程会超过 int 或 long (如果 int 或 long 型均为 4 字节存储空间) 型数据所能
// 表示的范围,故需要选择 long long (8 字节存储空间)型整数(除非你使用的算法在做乘的时候不
// 使用一般的乘法,而是使用替代方法实现原数的三倍加一)。
// 2. 输入时可能较大的数在前面,需要调整顺序,这个是导致算法正确却 WA 的重要原因。
// 3. 采用填表的方法保存既往计算结果,可以显著减少计算时间。
//
// 从网络上看了许多别人的解题方案,大多数都是忽略了第一点,求循环节长度的过程中,选择了 int 或
// long (按 32 位 CPU 来假定,4 字节存储空间)类型的数据,当计算 (n * 3 + 1) 时会超出 32
// 位整数的表示范围而得到错误答案,只不过 Programming Challenges 和 UVa 上的测试数据不是很强,
// 所以尽管不完善但都会获得 AC。在 1 - 999999 之间共有 41 个数在中间计算过程中会得到大于 32 位
// 无符号整数表示范围的整数,当测试数据包含这些数时,选用 int 或 long 类型有可能会得到错误的答案。
//
// 在中间计算过程中会超过 32 位整数表示范围的整数(括号内为循环节长度):
// 159487(184) 270271(407) 318975(185) 376831(330) 419839(162)
// 420351(242) 459759(214) 626331(509) 655359(292) 656415(292)
// 665215(442) 687871(380) 704511(243) 704623(504) 717695(181)
// 730559(380) 736447(194) 747291(248) 753663(331) 763675(318)
// 780391(331) 807407(176) 822139(344) 829087(194) 833775(357)
// 839679(163) 840703(243) 847871(326) 859135(313) 901119(251)
// 906175(445) 917161(383) 920559(308) 937599(339) 944639(158)
// 945791(238) 974079(383) 975015(321) 983039(290) 984623(290)
// 997823(440) #include <iostream> using namespace std; #define min(a, b) ((a) <= (b) ? (a) : (b))
#define max(a, b) ((a) >= (b) ? (a) : (b)) #define MAXSIZE 1000000 int cache[MAXSIZE]; // 计算循环节长度。
int counter(long long number)
{
if (number == )
return ; // 模 2 计算可用与计算代替,除 2 计算可用右移计算代替。
if (number & )
number += (number << ) + ;
else
number >>= ; // 若 number 在缓存范围内则根据情况取用。
if (number < MAXSIZE )
{
if (!cache[number])
cache[number] = counter(number);
return + cache[number];
} return + counter(number);
} int main(int ac, char *av[])
{
// 对于 GUN C++ 编译器,使用默认参数,在编译时会自动将全局数组 cache 中未初始化
// 的元素初始化为 0,故可以不需要显式的进行初始化的工作。对于其他编译器应该根据情况调整。
//
// memset(cache, 0, sizeof(cache));
//
int first, second, start, end; while (cin >> first >> second)
{
// 得到给定范围的上下界。
start = min(first, second);
end = max(first, second); // 查找最大步长值。
int result = , steps;
for (int i = start; i <= end; i++)
if ((steps = counter(i)) > result)
result = steps; // 输出。
cout << first << " " << second << " " << result << endl;
} return ;
}
100-The 3n + 1 problem的更多相关文章
- UVA 100 - The 3n+1 problem (3n+1 问题)
100 - The 3n+1 problem (3n+1 问题) /* * 100 - The 3n+1 problem (3n+1 问题) * 作者 仪冰 * QQ 974817955 * * [问 ...
- UVa 100 - The 3n + 1 problem(函数循环长度)
题目来源:https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=3&pa ...
- 【转】UVa Problem 100 The 3n+1 problem (3n+1 问题)——(离线计算)
// The 3n+1 problem (3n+1 问题) // PC/UVa IDs: 110101/100, Popularity: A, Success rate: low Level: 1 / ...
- PC/UVa 题号: 110101/100 The 3n+1 problem (3n+1 问题)
The 3n + 1 problem Background Problems in Computer Science are often classified as belonging to a ...
- uva 100 The 3n + 1 problem (RMQ)
uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem= ...
- UVa Problem 100 The 3n+1 problem (3n+1 问题)
参考:https://blog.csdn.net/metaphysis/article/details/6431937 #include <iostream> #include <c ...
- 烟大 Contest1024 - 《挑战编程》第一章:入门 Problem A: The 3n + 1 problem(水题)
Problem A: The 3n + 1 problem Time Limit: 1 Sec Memory Limit: 64 MBSubmit: 14 Solved: 6[Submit][St ...
- The 3n + 1 problem 分类: POJ 2015-06-12 17:50 11人阅读 评论(0) 收藏
The 3n + 1 problem Time Limit: 1000MS Memory Limit: 10000K Total Submissions: 53927 Accepted: 17 ...
- uva----(100)The 3n + 1 problem
The 3n + 1 problem Background Problems in Computer Science are often classified as belonging to a ...
随机推荐
- Server-U与IIS端口占用问题解决
在新版的ftp软件Server-U(11.X)中,由于其默认设置中监听了80端口,经常会导致IIS不能服务不能正常启用,下面记录如何修改server-u的80端口. 打开Server-U软件, ...
- Hadoop on Mac with IntelliJ IDEA - 9 解决Type mismatch in value from map问题
修改陆喜恒. Hadoop实战(第2版)5.3排序的代码时遇到IO异常. 环境:Mac OS X 10.9.5, IntelliJ IDEA 13.1.5, Hadoop 1.2.1 异常具体信息如下 ...
- IE6文字溢出BUG(多出来的猪问题)
在IE6下使用浮动可能会出现文字重复的情况. 在IE6下,浮动层之间有注释文字的话,之前那个浮动层的内容文字就有可能遭遇一个“隐形”的复制,但是代码里查看文字可并没有多出来. 看个例子: HTML & ...
- ssh-keygen 无密码登陆需要注意一个问题
从今天开始记录一下工程上的小知识. ssh-keygen -t rsa cat id_rsa.pub >> authorized_keys后,切记,将authrorized_keys文件的 ...
- 惊叹jQuery(解决jQuery对象到DOM的转换)
jQuery是一个javascript框架,但绝对不是通常意义上的一些包装,个人感觉是一个改变js控制方式的框架.我们可以像美工通过写css分离页面代码一样,通过jQuery来分离页面与效果..下面转 ...
- Codeforces Round #290 (Div. 2) D. Fox And Jumping dp
D. Fox And Jumping 题目连接: http://codeforces.com/contest/510/problem/D Description Fox Ciel is playing ...
- nested exception is java.io.FileNotFoundException: class path resource [spring/spring-datasource-mog
spring单元測试时发现的问题: org.springframework.beans.factory.BeanDefinitionStoreException: IOException parsin ...
- 【转】android开源项目和框架
特效: http://www.androidviews.net/ http://www.theultimateandroidlibrary.com/ 常用效果: 1. https://github ...
- ibatis 分页的简单实现
ibatis 物理分页的简单实现 cheungmine 2013-8-26 使用SSI (Struts2, Spring3, iBATIS2.3)框架开发Web服务的时候有一个需求就是对查询得到的结果 ...
- Lua游戏脚本语言入门(一)
作者: 沐枫 (第二人生成员) 原文地址:http://job.17173.com/content/2009-01-22/20090122143452606,1.shtml 在这篇文章中,我想向大家介 ...