[SDOI2010]猪国杀
Posted beretty
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[SDOI2010]猪国杀相关的知识,希望对你有一定的参考价值。
一个能看的题面 : https://mubu.com/doc/2707815814591da4
晚上闲的没事干被Refun忽悠着写猪国杀玩
然后一下子写到现在
浪费了一晚上+一上午
这题一堆肥肠SB的规则总之就是让你用他们的智商玩猪国杀
这是一篇没有任何意义的题解
附上10K的代码
然后那个忽悠我的人一直在嘲讽我写的长TAT
#include<map>
#include<cstdio>
#include<vector>
#include<cstring>
#include<iostream>
#include<algorithm>
const int M = 2005 ;
const int N = 15 ;
using namespace std ;
int n , m ;
int think[N] , pnum , znum , fnum ;
char resp[M] ;
bool Gameover ;
struct Pig {
int id ;
bool Isshow ;
bool cloth ;
int HP ;
bool dead ;
vector < char > c ;
} p[N] ;
inline bool Win() { if(fnum == 0 || p[1].HP == 0) Gameover = true ; return Gameover ; }
inline bool Isfriend (int a , int b) {
int x = p[a].id , y = p[b].id ;
if(x == 1 || x == 2) {
if(y == 1 || y == 2) return true ;
else return false ;
}
else {
if(y == 3) return true ;
else return false ;
}
}
inline bool Miss(int now) {
for(int i = 0 ; i < p[now].c.size() ; i ++) {
char ch = p[now].c[i] ;
if(ch == 'D') {
p[now].c.erase(p[now].c.begin() + i) ;
return true ;
}
}
return false ;
}
inline bool useK(int now) {
for(int i = 0 ; i < p[now].c.size() ; i ++) {
char ch = p[now].c[i] ;
if(ch == 'K') {
p[now].c.erase(p[now].c.begin() + i) ;
return true ;
}
}
return false ;
}
inline bool useJ(int now) {
for(int i = 0 ; i < p[now].c.size() ; i ++) {
char ch = p[now].c[i] ;
if(ch == 'J') {
p[now].c.erase(p[now].c.begin() + i) ;
return true ;
}
}
return false ;
}
inline bool recover(int now) {
for(int i = 0 ; i < p[now].c.size() ; i ++) {
char ch = p[now].c[i] ;
if(ch == 'P') {
p[now].HP ++ ;
p[now].c.erase(p[now].c.begin() + i) ;
return true ;
}
}
return false ;
}
inline void Getcard(int now , int NUM) {
for(int upp = 1 ; upp <= NUM ; pnum ++ , upp ++) {
p[now].c.push_back(resp[pnum]) ;
if(pnum == m) pnum = m - 1 ;
}
}
inline bool Kill(int now , int wh) {
int Np = 0 ;
for(int i = now + 1 ; i <= n ; i ++) if(!p[i].dead)
{ Np = i ; break ; }
if(!Np) for(int i = 1 ; i < now ; i ++) if(!p[i].dead)
{ Np = i ; break ; }
if(Np == 0) return false ;
if(now == 1) {
if(p[Np].Isshow && Isfriend(now , Np)) return false ;
else if(!p[Np].Isshow && !think[Np]) return false ;
else {
p[now].c.erase(p[now].c.begin() + wh) ;
if(Miss(Np)) return true ;
p[Np].HP -- ;
if(p[Np].HP == 0) {
if(recover(Np)) return true ;
else {
p[Np].dead = true ;
if(p[Np].id == 3) fnum-- ;
else {
znum -- ;
p[now].cloth = false ;
p[now].c.clear() ;
}
if(Win()) return true ;
if(!Gameover && p[Np].id == 3) Getcard(now , 3) ;
if(p[Np].id == 2)
{ p[now].c.clear() ; p[now].cloth = false ; }
}
}
}
}
else {
if(!p[Np].Isshow) return false ;
if(p[Np].Isshow && Isfriend(now , Np)) return false ;
if(p[Np].Isshow && !Isfriend(now , Np)) {
p[now].c.erase(p[now].c.begin() + wh) ;
if(!p[now].Isshow) p[now].Isshow = true ;
if(Miss(Np)) return true ;
else {
p[Np].HP -- ;
if(p[Np].HP == 0) {
if(recover(Np)) return true ;
else {
p[Np].dead = true ;
if(p[Np].id == 3) fnum -- ;
else znum -- ;
if(Win()) return true ;
if(!Gameover && p[Np].id == 3) Getcard(now , 3) ;
}
}
}
}
}
return true ;
}
inline bool Doj(int now , int Np) {
int wx = -1 ; bool Can = true ;
while(Can) {
Can = false ;
for(int i = now ; i <= n ; i ++) {
if(p[i].dead) continue ;
if(Isfriend(Np , i) && p[Np].Isshow && wx < 0) {
if(useJ(i)) {
wx = 1 ;
Can = true ;
p[i].Isshow = true ;
}
}
if(!Isfriend(Np , i) && p[Np].Isshow && wx > 0) {
if(useJ(i)) {
wx = -1 ;
Can = true ;
p[i].Isshow = true ;
}
}
}
if(Can) continue ;
for(int i = 1 ; i < now ; i ++) {
if(p[i].dead) continue ;
if(Isfriend(Np , i) && p[Np].Isshow && wx < 0) {
if(useJ(i)) {
wx = 1 ;
Can = true ;
p[i].Isshow = true ;
}
}
if(!Isfriend(Np , i) && p[Np].Isshow && wx > 0) {
if(useJ(i)) {
wx = -1 ;
Can = true ;
p[i].Isshow = true ;
}
}
}
}
if(wx < 0) return false ;
return true ;
}
inline void Dofight(int now, int Np) {
int End = Np ;
if(now != 1 && p[Np].id != 2)
while(1) {
if(!useK(Np))
{ End = Np ; break ; }
if(!useK(now))
{ End = now ; break ; }
}
p[End].HP -- ;
int retp ;
if(End == now) retp = Np ;
else retp = now ;
if(p[End].HP == 0) {
if(recover(End)) return ;
p[End].dead = true ;
if(p[End].id == 3) fnum -- ;
else znum -- ;
if(Win()) return ;
if(!Gameover && p[End].id == 3) Getcard(retp , 3) ;
if(p[End].id == 2 && retp == 1)
{ p[retp].c.clear() ; p[retp].cloth = false ; }
}
}
inline bool Fight(int now , int wh) {
int Np = 0 ;
if(now == 1) {
for(int i = now + 1 ; i <= n ; i ++) {
if(p[i].dead) continue ;
if(p[i].Isshow && Isfriend(now , i)) continue ;
if(!p[i].Isshow && !think[i]) continue ;
Np = i ; break ;
}
if(!Np)
for(int i = 1 ; i < now ; i ++) {
if(p[i].dead) continue ;
if(p[i].Isshow && Isfriend(now , i)) continue ;
if(!p[i].Isshow && !think[i]) continue ;
Np = i ; break ;
}
}
else if(p[now].id == 2){
for(int i = now + 1 ; i <= n ; i ++) {
if(p[i].dead) continue ;
if(!p[i].Isshow) continue ;
if(Isfriend(now , i)) continue ;
Np = i ; break ;
}
if(!Np)
for(int i = 1 ; i < now ; i ++) {
if(p[i].dead) continue ;
if(!p[i].Isshow) continue ;
if(Isfriend(now , i)) continue ;
Np = i ; break ;
}
}
else if(p[now].id == 3) {
Np = 1 ;
if(!p[now].Isshow) p[now].Isshow = true ;
}
if(!Np) return false ;
p[now].c.erase(p[now].c.begin() + wh) ;
if(p[Np].id == 2 && !p[Np].Isshow) Dofight(now , Np) ;
else if(!Doj(now , Np)) Dofight(now , Np) ;
return true ;
}
inline void North(int now , int wh) {
p[now].c.erase(p[now].c.begin() + wh) ;
for(int i = now + 1 ; i <= n ; i ++) {
if(p[i].dead) continue ;
if(!Doj(now , i)) {
if(useK(i)) continue ;
else {
p[i].HP -- ;
if(p[i].id == 1) think[now] = true ;
if(p[i].HP == 0) {
if(recover(i)) continue ;
p[i].dead = true ;
if(p[i].id == 3) fnum -- ;
else znum -- ;
if(Win()) return ;
if(!Gameover && p[i].id == 3)
Getcard(now , 3) ;
if(p[i].id == 2 && now == 1)
{ p[now].c.clear() ; p[now].cloth = false ; }
}
}
}
}
for(int i = 1 ; i < now ; i ++) {
if(p[i].dead) continue ;
if(!Doj(now , i)) {
if(useK(i)) continue ;
else {
p[i].HP -- ;
if(p[i].id == 1) think[now] = true ;
if(p[i].HP == 0) {
if(recover(i)) continue ;
p[i].dead = true ;
if(p[i].id == 3) fnum -- ;
else znum -- ;
if(Win()) return ;
if(!Gameover && p[i].id == 3)
Getcard(now , 3) ;
if(p[i].id == 2 && now == 1)
{ p[now].c.clear() ; p[now].cloth = false ; }
}
}
}
}
}
inline void WJQF(int now , int wh) {
p[now].c.erase(p[now].c.begin() + wh) ;
for(int i = now + 1 ; i <= n ; i ++) {
if(p[i].dead) continue ;
if(!Doj(now , i)) {
if(Miss(i)) continue ;
else {
p[i].HP -- ;
if(p[i].id == 1) think[now] = true ;
if(p[i].HP == 0) {
if(recover(i)) continue ;
p[i].dead = true ;
if(p[i].id == 3) fnum -- ;
else znum -- ;
if(Win()) return ;
if(!Gameover && p[i].id == 3)
Getcard(now , 3) ;
if(p[i].id == 2 && now == 1)
{ p[now].c.clear() ; p[now].cloth = false ; }
}
}
}
}
for(int i = 1 ; i < now ; i ++) {
if(p[i].dead) continue ;
if(!Doj(now , i)) {
if(Miss(i)) continue ;
else {
p[i].HP -- ;
if(p[i].id == 1) think[now] = true ;
if(p[i].HP == 0) {
if(recover(i)) continue ;
p[i].dead = true ;
if(p[i].id == 3) fnum -- ;
else znum -- ;
if(Win()) return ;
if(!Gameover && p[i].id == 3)
Getcard(now , 3) ;
if(p[i].id == 2 && now == 1)
{ p[now].c.clear() ; p[now].cloth = false ; }
}
}
}
}
}
inline void Solve(int now) {
bool Can = true ;
bool killuse = false ;
while(Can) {
Can = false ;
if(Win()) return ;
for(int i = 0 ; i < p[now].c.size() ; i ++) {
if(Win()) return ;
if(p[now].dead) return ;
char ch = p[now].c[i] ;
if(ch == 'P') {
if(p[now].HP < 4) {
p[now].HP ++ ;
p[now].c.erase(p[now].c.begin() + i) ;
Can = true ; break ;
}
}
else if(ch == 'K') {
if(killuse == true && p[now].cloth == false) continue ;
if(Kill(now , i)) {
Can = true ;
killuse = true ; break ;
}
}
else if(ch == 'F') {
if(Fight(now , i) ) {
Can = true ;
break ;
}
}
else if(ch == 'N') {
North(now , i) ;
Can = true ;
break ;
}
else if(ch == 'W') {
WJQF(now , i) ;
Can = true ;
break ;
}
else if(ch == 'Z') {
p[now].cloth = true ; Can = true ;
p[now].c.erase(p[now].c.begin() + i) ; break ;
}
}
}
}
int main() {
scanf("%d%d",&n,&m) ; pnum = 1 ;
for(int i = 1 ; i <= n ; i ++) {
p[i].HP = 4 ; p[i].Isshow = false ;
p[i].cloth = false ; p[i].dead = false ;
char s1[5] , s[6][5] ;
scanf("%s%s%s%s%s",s1,s[1],s[2],s[3],s[4]) ;
if(s1[0] == 'M') p[i].id = 1 , znum ++ ;
else if(s1[0] == 'Z') p[i].id = 2 , znum ++ ;
else p[i].id = 3 , fnum ++ ;
for(int j = 1 ; j <= 4 ; j ++) p[i].c.push_back(s[j][0]) ;
}
p[1].Isshow = true ;
for(int i = 1 ; i <= m ; i ++) {
char s[5] ;
scanf("%s",s) ;
resp[i] = s[0] ;
}
int now = 1 ;
while(!Gameover) {
if(Win()) break ;
while(p[now].dead) {
++ now ;
if(now > n) now = 1 ;
}
Getcard(now , 2) ;
Solve(now) ;
++ now ;
if(now > n) now = 1 ;
}
if(p[1].HP == 0) printf("FP
") ;
else printf("MP
") ;
for(int i = 1 ; i <= n ; i ++) {
if(p[i].dead) printf("DEAD
") ;
else {
for(int j = 0 ; j < p[i].c.size() ; j ++)
printf("%c ",p[i].c[j]) ;
printf("
") ;
}
}
return 0 ;
}
以上是关于[SDOI2010]猪国杀的主要内容,如果未能解决你的问题,请参考以下文章