HDU - 4431 and HDU - 3391 我们一起打麻将 【dfs暴力模拟】
2017-10-06 20:54
309 查看
HDU - 4431
HDU - 3391
//这两道题是非常相似的, hdu4431要更难一点, 就以这道题来讲解, 会了这道题, 下面那道题也应该会了. 还有一道Uva的11210(题解) 很像, 但是数据相对弱很多, 不加剪枝也能过, 而hdu4431必须要剪枝, 否则会T.
思路:
1:题目意思是问你什么牌能胡, 所以34张牌一张一张枚举过去就行了
2:胡牌的方式有三种 :
第一:七对不同的,四个相同的不算两对
第二:十三幺,1、9筒,1、9条,1、9万,东南西北红中白板发财,这十三张牌里面有一
种牌是两张其余的都是一张
第三:简单的胡牌,先找出一个对, 剩下下的十二张牌组成顺子或者小包子(即三个一样的)
注意点:
1: 每一种牌不能超过4张, 这里特判一下.
2: 组成顺子的只能是筒,条,万. 那特殊的7张牌不能组成顺子. 但可以组成小包子.
3: 找到一个对子后进行dfs查找顺子或者小包子的时候特别要注意一定要剪枝,否则T到死.
AC Code
HDU - 3391
//这两道题是非常相似的, hdu4431要更难一点, 就以这道题来讲解, 会了这道题, 下面那道题也应该会了. 还有一道Uva的11210(题解) 很像, 但是数据相对弱很多, 不加剪枝也能过, 而hdu4431必须要剪枝, 否则会T.
思路:
1:题目意思是问你什么牌能胡, 所以34张牌一张一张枚举过去就行了
2:胡牌的方式有三种 :
第一:七对不同的,四个相同的不算两对
第二:十三幺,1、9筒,1、9条,1、9万,东南西北红中白板发财,这十三张牌里面有一
种牌是两张其余的都是一张
第三:简单的胡牌,先找出一个对, 剩下下的十二张牌组成顺子或者小包子(即三个一样的)
注意点:
1: 每一种牌不能超过4张, 这里特判一下.
2: 组成顺子的只能是筒,条,万. 那特殊的7张牌不能组成顺子. 但可以组成小包子.
3: 找到一个对子后进行dfs查找顺子或者小包子的时候特别要注意一定要剪枝,否则T到死.
AC Code
const int maxn = 100+5; int cas=1; char *Ma[] = {"1m","2m","3m","4m","5m","6m","7m","8m","9m", "1s","2s","3s","4s","5s","6s","7s","8s","9s", "1p","2p","3p","4p","5p","6p","7p","8p","9p", "1c","2c","3c","4c","5c","6c","7c"}; inline int change(char *s) { for(int i=0;i<34;i++){ if(strcmp(s,Ma[i]) == 0) return i; } } bool check(int x) //判断是否可以组成顺子. { if(x>=0 && x<=6) return true; else if(x>=9 && x<= 15) return true; else if(x>=18 && x <= 24) return true; else return false; } int c[maxn]; inline bool dfs(int deep) { if(deep >=4) return true; int flag = 0; for(int i=0;i<34;i++){ int ff = 0; if(c[i]>=3){ ff++; c[i] -= 3; if(dfs(deep+1)) return true; c[i] += 3; } if(check(i) && c[i] > 0 && c[i+1] > 0 && c[i+2] > 0){ ff++; c[i]--; c[i+1]--; c[i+2]--; if(dfs(deep+1)) return true; c[i]++; c[i+1]++; c[i+2]++; } //以下两个个剪枝是最重要的, 否则会T. if(c[i] && !ff) return false; //这种牌有但是不符合顺子或者小包子结束这层搜索 if(c[i]) break; //这里减枝是因为上面的搜索下次遍历的时候还会继续从他这遍历,所以就不用继续下去 } return false; } inline bool check1() { for(int i=0;i<34;i++){ if(c[i]>=2) { c[i] -= 2; if(dfs(0)) return true; c[i] += 2; } } return false; } inline bool check2(int x) { int cnt1 = 0,cnt2 = 0,sum = 0; for(int i=0;i<34;i++){ if(c[i] == 2) cnt1++; if(i>=27 && c[i] >0) cnt2++,sum+=c[i]; if((i <= 26 && (i%9 == 0 || i%9 == 8)) && c[i] > 0) cnt2++,sum+=c[i]; } if(cnt1 == 7 || (cnt2 == 13 && sum == 14)) return true; return false; } int ans[maxn]; void solve() { int mj[maxn]; for(int i=0;i<13;i++){ char s[10]; scanf("%s",s); mj[i] = change(s); } bool flag = 0; int cnt = 0; for(int i=0;i<34;i++){ Fill(c,0); for(int j=0;j<13;j++) c[mj[j]]++; if(c[i]>=4) continue; c[i]++; if(check2(i)) { flag = 1; ans[cnt++] = i; } else if(check1()) { flag = 1; ans[cnt++] = i; } } if(!flag) puts("Nooten"); else{ printf("%d",cnt); for(int i=0;i<cnt;i++){ printf(" %s",Ma[ans[i]]); } printf("\n"); } }
相关文章推荐
- hdu 4431 Mahjong(dfs+模拟)
- HDU 4801 Pocket Cube(暴力模拟 dfs)
- hdu 4431 Mahjong (模拟,枚举+dfs)
- HDU 4431 Mahjong (DFS,暴力枚举,剪枝)
- hdu 4770 Lights Against Dudely(暴力枚举dfs)
- hdu 4272 LianLianKan(模拟dfs+map)
- HDU 1010 Tempter of the Bone(DFS+暴力+标记)
- HDU 4431 Mahjong 搜索 模拟
- hdu 3274 city planning 暴力+DFS
- HDU 4403 A very hard Aoshu problem (DFS暴力)
- hdu 5311 Hidden String(dp+暴力dfs)
- [HDU 1427]速度计算24点(DFS暴力搜索)
- 2015多校第6场 HDU 5355 Cake 贪心,暴力DFS
- HDU 4509 湫湫系列故事——减肥记II(暴力模拟即可)
- hdu 4462 Scaring the Birds【Dfs+暴力判断】
- hdu 4770 Lights Against Dudely(暴力枚举dfs)
- HDU 5547 (DFS暴力)
- HDU 1045(二分图求最小点覆盖问题;dfs暴力)
- E - Digital Square --模拟暴力dfs
- HDU 4414 Finding crosses (暴力模拟)