uva100 The 3n + 1 problem

记忆化搜索,就是说如果f[n]已经计算过,直接使用, 另外注意数组越界问题。

为了加快查询速度,使用RMQ, 即区间最值。用动态规划的方法来查询某个区间的最值。

pku1207也是这道题目,不过规模变小了很多。

 

#include <stdio.h> #include <math.h> #define MAXN 1000001 unsigned long f[MAXN]; unsigned long fij[21][MAXN]; unsigned long calc(unsigned long n) { unsigned long sum = 0; if (f[n] != 0) return f[n]; while (n>=MAXN || f[n]==0) { if (n%2 == 1) n = 3*n + 1; else n = n/2; sum++; } return sum+f[n]; } #define VMAX(a,b) ((a)>(b)?(a):(b)) int main() { int i, j, k, a, b; unsigned long vmax; f[1] = 1; for (i=2; i<MAXN; i++) { f[i] = calc(i); } for (i=1; i<MAXN; i++) { fij[0][i] = f[i]; } for (i=1; i<=log((double)MAXN)/log(2.0); i++) for (j=1; j<MAXN; j++) { fij[i][j] = VMAX(fij[i-1][j], fij[i-1][j+(1<<(i-1))]); } while (scanf("%d %d", &a, &b)!=EOF) { printf("%d %d ", a, b); if (a>b) { k = a; a = b; b = k; } k = log((double)(b-a+1))/log(2.0); vmax = VMAX(fij[k][a], fij[k][b-(1<<k)+1]); printf("%d/n", vmax); } return 0; }

你可能感兴趣的:(uva100 The 3n + 1 problem)