HDU 4431 Mahjong(枚举+模拟)(2012 Asia Tianjin Regional Contest)

One to nine Man, which we use 1m to 9m to represent;

One to nine Sou, which we use 1s to 9s to represent;

One to nine Pin, which we use 1p to 9p to represent;

Character tiles, which are:Ton, Nan, Sei, Pei, Haku, Hatsu, Chun, which we use 1c to 7c to represent.
A winning state means a set of 14 tiles that normally contains a pair of same tiles (which we call "eyes") and four melds. A meld is formed by either three same tiles(1m, 1m, 1m or 2c, 2c, 2c for example) or three continuous non-character tiles(1m, 2m, 3m or 5s, 6s, 7s for example).
However, there are two special winning states that are different with the description above, which are:
"Chii Toitsu", which means 7 different pairs of tiles;
"Kokushi Muso", which means a set of tiles that contains all these tiles: 1m, 9m, 1p, 9p, 1s, 9s and all 7 character tiles. And the rest tile should also be one of the 13 tiles above.
And the game starts with four players receiving 13 tiles. In each round every player must draw one tile from the deck one by one. If he reaches a winning state with these 14 tiles, he can say "Tsu Mo" and win the game. Otherwise he should discard one of his 14 tiles. And if the tile he throws out can form a winning state with the 13 tiles of any other player, the player can say "Ron" and win the game.
Now the question is, given the 13 tiles you have, does there exist any tiles that can form a winning state with your tiles?
(Notes: Some of the pictures and descriptions above come from Wikipedia.)
#include <cstdio>
#include <iostream>
#include <algorithm>
#include <cstring>
#include <vector>
using namespace std;
typedef long long LL; const int MAXN = ; struct TILES {
int P[MAXN], M[MAXN], S[MAXN], C[MAXN]; void init() {
#define CL(a) memset(a, 0, sizeof(a))
CL(P), CL(M), CL(S), CL(C);
} void read() {
char str[];
for(int i = ; i < ; ++i) {
scanf("%s", str);
switch(str[]) {
case 'p':++P[str[] - ''];break;
case 'm':++M[str[] - ''];break;
case 's':++S[str[] - ''];break;
case 'c':++C[str[] - ''];break;
}
}
} bool special_judge1() {
int cnt = ;
for(int i = ; i <= ; ++i) {
cnt += (M[i] == );
cnt += (S[i] == );
cnt += (P[i] == );
cnt += (C[i] == );
}
return cnt == ;
} bool special_judge2() {
bool eyes = false;
for(int i = ; i <= ; ++i) {
if(C[i] == || C[i] > ) return false;
if(C[i] == ) eyes = true;
}
if(M[] == || M[] > ) return false;
if(M[] == || M[] > ) return false;
if(S[] == || S[] > ) return false;
if(S[] == || S[] > ) return false;
if(P[] == || P[] > ) return false;
if(P[] == || P[] > ) return false;
if(M[] == || M[] == ) eyes = true;
if(S[] == || S[] == ) eyes = true;
if(P[] == || P[] == ) eyes = true;
return eyes;
} int UP[MAXN], UM[MAXN], US[MAXN]; bool isWin() {
int x;
for(int i = ; i <= ; ++i) {
if(P[i] - UP[i] >= ) UP[i] += ;
if(S[i] - US[i] >= ) US[i] += ;
if(M[i] - UM[i] >= ) UM[i] += ;
x = P[i] - UP[i];
if(x != ) {
UP[i] += x;
if((UP[i + ] += x) > P[i + ]) return false;
if((UP[i + ] += x) > P[i + ]) return false;
}
x = S[i] - US[i];
if(x != ) {
US[i] += x;
if((US[i + ] += x) > S[i + ]) return false;
if((US[i + ] += x) > S[i + ]) return false;
}
x = M[i] - UM[i];
if(x != ) {
UM[i] += x;
if((UM[i + ] += x) > M[i + ]) return false;
if((UM[i + ] += x) > M[i + ]) return false;
}
}
return true;
} bool judge() {
if(special_judge1() || special_judge2()) return true;
bool eyes = false;
for(int i = ; i <= ; ++i) {
if(C[i] == ) {
if(!eyes) eyes = true;
else return false;
}
if(C[i] == || C[i] == ) return false;
}
if(eyes) {
CL(UP), CL(UM), CL(US);
return isWin();
}
for(int i = ; i <= ; ++i) {
if(P[i] >= ) {
CL(UP), CL(UM), CL(US);
UP[i] = ;
if(isWin()) return true;
}
}
for(int i = ; i <= ; ++i) {
if(S[i] >= ) {
CL(UP), CL(UM), CL(US);
US[i] = ;
if(isWin()) return true;
}
}
for(int i = ; i <= ; ++i) {
if(M[i] >= ) {
CL(UP), CL(UM), CL(US);
UM[i] = ;
if(isWin()) return true;
}
}
return false;
} vector<int> ans2;
vector<char> ans1; void solve() {
ans1.clear();
ans2.clear();
for(int i = ; i <= ; ++i) {
++M[i];
if(M[i] <= && judge()) {
ans1.push_back('m');
ans2.push_back(i);
}
--M[i];
}
for(int i = ; i <= ; ++i) {
++S[i];
if(S[i] <= && judge()) {
ans1.push_back('s');
ans2.push_back(i);
}
--S[i];
}
for(int i = ; i <= ; ++i) {
++P[i];
if(P[i] <= && judge()) {
ans1.push_back('p');
ans2.push_back(i);
}
--P[i];
}
for(int i = ; i <= ; ++i) {
++C[i];
if(C[i] <= && judge()) {
ans1.push_back('c');
ans2.push_back(i);
}
--C[i];
}
} void print() {
int len = ans1.size();
if(len == ) {
puts("Nooten");
return ;
}
printf("%d", len);
for(int i = ; i < len; ++i)
printf(" %d%c", ans2[i], ans1[i]);
puts("");
}
} G; int main() {
int T;
scanf("%d", &T);
while(T--) {
G.init();
G.read();
G.solve();
G.print();
}
}
HDU 4431 Mahjong(枚举+模拟)(2012 Asia Tianjin Regional Contest)的更多相关文章
- HDU-4432-Sum of divisors ( 2012 Asia Tianjin Regional Contest )
Sum of divisors Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) ...
- HDU 4433 locker 2012 Asia Tianjin Regional Contest 减少国家DP
意甲冠军:给定的长度可达1000数的顺序,图像password像锁.可以上下滑动,同时会0-9周期. 每个操作.最多三个数字连续操作.现在给出的起始序列和靶序列,获得操作的最小数量,从起始序列与靶序列 ...
- HDU 4436 str2int(后缀自动机)(2012 Asia Tianjin Regional Contest)
Problem Description In this problem, you are given several strings that contain only digits from '0' ...
- HDU 4433 locker(DP)(2012 Asia Tianjin Regional Contest)
Problem Description A password locker with N digits, each digit can be rotated to 0-9 circularly.You ...
- HDU 4441 Queue Sequence(优先队列+Treap树)(2012 Asia Tianjin Regional Contest)
Problem Description There's a queue obeying the first in first out rule. Each time you can either pu ...
- HDU 3721 Building Roads (2010 Asia Tianjin Regional Contest) - from lanshui_Yang
感慨一下,区域赛的题目果然很费脑啊!!不过确实是一道不可多得的好题目!! 题目大意:给你一棵有n个节点的树,让你移动树中一条边的位置,即将这条边连接到任意两个顶点(边的大小不变),要求使得到的新树的直 ...
- HDU 3726 Graph and Queries(平衡二叉树)(2010 Asia Tianjin Regional Contest)
Description You are given an undirected graph with N vertexes and M edges. Every vertex in this grap ...
- HDU 4468 Spy(KMP+贪心)(2012 Asia Chengdu Regional Contest)
Description “Be subtle! Be subtle! And use your spies for every kind of business. ”― Sun Tzu“A spy w ...
- HDU 4467 Graph(图论+暴力)(2012 Asia Chengdu Regional Contest)
Description P. T. Tigris is a student currently studying graph theory. One day, when he was studying ...
随机推荐
- c语言描述的静态查找表
顺序表的查找: 直接循环依次和目标比较就行 有序表的查找(二分查找): int search(SS *T,Type key){ int mid; ; int high=T.length; while( ...
- Spring框架中的IOC?
Spring中的org.springframework.beans包和org.SpringframeWork.context包构成了Spring框架IOC容器的基础.BeanFactory接口提供了一 ...
- Vue组件:组件的动态添加与删除
一.实现效果 二.实现代码 HelloWorld.vue <template> <div class="hello"> <child-page v-f ...
- 构建高可靠hadoop集群之4-权限指引
此文翻译自http://hadoop.apache.org/docs/r2.8.0/hadoop-project-dist/hadoop-hdfs/HdfsPermissionsGuide.html ...
- ArrayList调用remove(int index)抛出UnsupportedOperationException问题分析以及解决记录
使用Arrays转数组成为List后,不能调用add(...)和remove(...)方法,此时如果调用就会抛出UnsupportedOperationException异常 原因 其实Arrays. ...
- sql sever 基础 建表
---恢复内容开始--- SQL Sever 基础以创建银行数据库bankDB为案例 1.创建数据库 1-1 创建文件夹用以存放数据库 1-2 创建建库bankDB 2.创建数据库 2-1.创建用户信 ...
- Linux系统磁盘管理
1 Linux磁盘管理体系简介 Linux磁盘管理分为五个步骤:首先在服务器上添加相应的硬盘(如/dev/sda.sdb.sdc等),对全新的服务器(即没有操作系统)做硬RAID0.RAID1.RAI ...
- POCO TCPServer 解析
POCO C++ Libraries提供一套 C++ 的类库用以开发基于网络的可移植的应用程序,功能涉及线程.文件.流,网络协议包括:HTTP.FTP.SMTP 等,还提供 XML 的解析和 SQL ...
- ethereum Pet Shop
在部署宠物商店时遇到的一些坑,给大家总结一下,以免大家多走弯路 转载的地址(详细):https://steemit.com/cn/@lucia3/ethereum-pet-shop 启动"n ...
- 系统编程.py(多进程与多线程干货)
1.并发与并行* 多个任务轮换在CPU上跑叫并发* 多个任务在多个CPU上跑,没有交替执行的* 状态叫并行.通常情况下都是并发,即使是多核.* 而控制进程先执行谁后执行谁通过操作系统的调度算法.目前已 ...