[hdu1401] Solitaire

hdu 1401 传送门

poj 1198 传送门

uva 1724 传送门

折半搜索就好了。

用个map记忆一下。

记录旗子的位置再排序也能做。

但是考虑到8*8正好能用long long压一下,所以我是状压了棋盘。

注意如果用dfs不要判重,有可能状态一样,但是步数不同。

 1 #include<cstdio>
 2 #include<cstring>
 3 #include<algorithm>
 4 #include<map>
 5 using namespace std;
 6 typedef unsigned long long ull;
 7 const ull u=1ull;
 8 
 9 int ans;
10 ull st,ed;
11 map<ull,int>mp;
12 
13 int dfs(ull s,int kd,int r)
14 {
15     if(mp[s]==3-kd)return 1;
16     mp[s]=kd;
17     if(!r)return 0;
18     r--;
19     int ret=0;
20     for(int i=0;i<64;i++)
21     {
22         if(!(s&(u<<i)))continue;
23         ull to=s^(u<<i);
24         if(i%8<7&&(!(s&(u<<i+1))))
25             ret|=dfs(to|(u<<i+1),kd,r);
26         if(i%8<6&&(s&(u<<i+1))&&(!(s&(u<<i+2))))
27             ret|=dfs(to|(u<<i+2),kd,r);
28         if(i%8>0&&(!(s&(u<<i-1))))
29             ret|=dfs(to|(u<<i-1),kd,r);
30         if(i%8>1&&(s&(u<<i-1))&&(!(s&(u<<i-2))))
31             ret|=dfs(to|(u<<i-2),kd,r);
32         if(i>=8&&(!(s&(u<<i-8))))
33             ret|=dfs(to|(u<<i-8),kd,r);
34         if(i>=16&&(s&(u<<i-8))&&(!(s&(u<<i-16))))
35             ret|=dfs(to|(u<<i-16),kd,r);
36         if(i+8<64&&(!(s&(u<<i+8))))
37             ret|=dfs(to|(u<<i+8),kd,r);
38         if(i+16<64&&(s&(u<<i+8))&&(!(s&(u<<i+16))))
39             ret|=dfs(to|(u<<i+16),kd,r);
40     }
41     return ret;
42 }
43 
44 int main()
45 {
46     int pos[4][2];
47     while(scanf("%d%d",&pos[0][0],&pos[0][1])!=EOF)
48     {
49         mp.clear();
50         ans=st=ed=0;
51         for(int i=1;i<4;i++)
52             scanf("%d%d",&pos[i][0],&pos[i][1]);
53         for(int i=0;i<4;i++)
54             for(int j=0;j<2;j++)pos[i][j]--;
55         for(int i=0;i<4;i++)
56             st|=(u<<((pos[i][0]<<3)+pos[i][1]));
57         for(int i=0;i<4;i++)
58             scanf("%d%d",&pos[i][0],&pos[i][1]);
59         for(int i=0;i<4;i++)
60             for(int j=0;j<2;j++)pos[i][j]--;
61         for(int i=0;i<4;i++)
62             ed|=(u<<((pos[i][0]<<3)+pos[i][1]));
63         dfs(st,1,4);
64         ans=dfs(ed,2,4);
65         printf(ans?"YES\n":"NO\n");
66     }
67     return 0;
68 }

猜你喜欢

转载自www.cnblogs.com/eternhope/p/10003504.html