poj 3134 && LA 3621 Power Calculus (迭代加深深度优先搜索)

https://icpcarchive.ecs.baylor.edu/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1622

3134 -- Power Calculus

  又搞了几天才出一题。

  这题我是用迭代加深深度优先搜索来做的。网上的题解多种多样,大部分都是BFS的,不过好多都是没有证明的方法。表示个人认为迭代加深是一个十分好的正解。

  至于这题为何用迭代加深,个人认为原因是:

(1)BFS剪枝不容易加上去,即便是加上一两个剪枝也无法剪枝到系统可以接受的时间和空间。(网上有题解说搜索到多少个后停止搜索的方法,可惜没有详细的证明,故认为那是水过的)

(2)IDDFS与BFS相比,因为是在搜索的过程中直接记录路径,所以相对BFS节省了大量空间。

  除此以外,表示打了好几个版本的代码,IDDFS是相当轻便的一种方法。

View Code
 1 #include <cstdio>
 2 #include <cstring>
 3 #include <algorithm>
 4 #include <iostream>
 5 #include <vector>
 6 #include <cmath>
 7 
 8 using namespace std;
 9 
10 const int N = 1 << 11;
11 int ep2[15], lg2[N];
12 #define REP(i, n) for (int i = 0; i < (n); i++)
13 #define REP_1(i, n) for (int i = 1; i <= (n); i++)
14 #define DEC(i, a, b) for (int i = (a); i >= (b); i--)
15 #define PB push_back
16 #define SZ(x) ((int) (x).size())
17 
18 void PRE() {
19     REP(i, 15) {
20         ep2[i] =  1 << i;
21     }
22     int t = 0;
23     REP(i, N) {
24         if (ep2[t + 1] <= i) t++;
25         lg2[i] = t;
26     }
27 //    REP(i, 10) cout << lg2[i] << endl;
28 }
29 
30 int st[20], top;
31 
32 bool dfs(int n, int depth) {
33     if (st[top] == n) return true;
34     if (top >= depth) return false;
35     int last = st[top];
36     if ((last << (depth - top)) < n) return false;
37     if (st[top] <= 1200) {
38         DEC(i, top, 0) {
39             st[++top] = last + st[i];
40             if (dfs(n, depth)) return true;
41             top--;
42         }
43     }
44     REP(i, top + 1) {
45         st[++top] = last - st[i];
46         if (st[top] > 1) {
47             if (dfs(n, depth)) return true;
48         }
49         top--;
50     }
51     return false;
52 }
53 
54 int main() {
55 //    freopen("out", "w", stdout);
56     int n;
57     PRE();
58 //    REP_1(n, 1000) {
59 //        int step = lg2[n];
60 //        while (step <= 12) {
61 //            st[top = 0] = 1;
62 //            if (dfs(n, step)) break;
63 //            step++;
64 //        }
65 //        cout << n << ' ' << step << endl;
66 //    }
67 //    return 0;
68     while (cin >> n && n) {
69         int step = lg2[n];
70         while (step <= 12) {
71             st[top = 0] = 1;
72             if (dfs(n, step)) break;
73             step++;
74         }
75         cout << step << endl;
76     }
77     return 0;
78 }

 

——written by Lyon

 

转载于:https://www.cnblogs.com/LyonLys/archive/2013/05/06/poj_3134_LA_3621_Lyon.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值