HDU 5965 扫雷

这种题乍一看都是整体性非常的强,有每一步都有很多种情况,但是又必须要为结果的成功作铺垫,这样直接分析的话确实很复杂。

因为一共只有三行,那么从最左边的一列开始分析,这一列可以填的雷可以有0,1,2对应的方案数分别是1,2,1,那么如果第一列确定了,那么第二列

根据第一列第二行已经有的数据,也确定了,如此发现就是当第一列的状态确定那么整个序列就可以确定,至于方案的成功与否只需要检测

在过程中间推导是否有矛盾,和最后一列的情况是否符合。

这种确定一个状态,整个系统状态就大体确定的,符合开关问题,因此只需要枚举第一列填的个数即可。

 1 #include <stdio.h>
 2 #include <string.h>
 3 #include <iostream>
 4 #include <queue>
 5 #include <vector>
 6 #include <algorithm>
 7 #include <stack>
 8 #include <set>
 9 #include <map>
10 #include <math.h>
11 #define pb push_back
12 #define CLR(a) memset(a, 0, sizeof(a));
13 #define MEM(a, b) memset(a, b, sizeof(a));
14 #define fi first
15 #define se second
16 
17 using namespace std;
18 
19 typedef long long ll;
20 
21 const int MAXN = 10007;
22 const int MAXV = 207;
23 const int MAXE = 207;
24 const int INF = 0x3f3f3f3f;
25 const ll MOD = 1e8+7;
26 
27 char s[MAXN];
28 
29 int a[MAXN];
30 ll vars[3] = {1, 2, 1};
31 ll ans = 0;
32 int t[MAXN];
33 int len;
34 ll solve()
35 {
36     ll ret = 0;
37     for (int i = 1; i < len; i++)
38     {
39         if (i == 1 && (a[i-1] < t[i-1] || (t[i-1] + 2) < a[i-1]) ) return 0;
40         else if (i != 1 && (a[i-1] < (t[i-1]+t[i-2]) || (t[i-2]+t[i-1]+2) < a[i-1])) return 0;
41         if (i == 1) t[i] = a[i-1] - t[i-1];
42         else t[i] = a[i-1] - t[i-1] - t[i-2];
43     }
44     if (len == 1 && t[0] != a[0]) return 0; 
45     if (t[len-1]+t[len-2] != a[len-1]) return 0;
46     ret = vars[t[0]];
47     for (int i = 1; i < len; i++)
48     {
49         ret = (ret * vars[t[i]]) % MOD;
50     }
51     return ret % MOD;
52 }
53 
54 
55 int main()
56 {
57     //freopen("in.txt", "r", stdin);
58     int T;
59     scanf("%d", &T);
60     while (T--)
61     {
62         scanf("%s", s);
63         len = strlen(s);
64         for (int i = 0; i < len; i++)
65             a[i] = s[i] - '0';
66         ans = 0;
67         for (int i = 0; i < 3; i++)
68         {
69             t[0] = i;
70             ll tmp = solve();
71             //cout << tmp << endl;
72             ans = (ans + tmp) % MOD;
73         //    cout << i << " " << ans << endl;
74         }
75         cout << ans << endl;
76     }
77     return 0;
78 }
原文地址:https://www.cnblogs.com/oscar-cnblogs/p/7615128.html