题解

枚举x所在的地图的颜色,然后2-SAT建边

如果v所在的地图刚好是不能选的,那么u这边只能选另一种颜色

否则就是u的颜色到v的颜色

v的另一种颜色到u的另一种颜色

代码

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
#include <cmath>
#include <ctime>
#include <vector>
//#define ivorysi
#define MAXN 100005
#define eps 1e-7
#define mo 974711
#define pb push_back
using namespace std;
typedef long long int64;
typedef unsigned int u32;
typedef double db;
int N,D,M;
char s[MAXN],c[2][MAXN][4],L[MAXN];
int u[MAXN],v[MAXN];
struct node {
int to,next;
}E[MAXN * 2];
int head[MAXN * 2],sumE;
void add(int u,int v) {
E[++sumE].to = v;
E[sumE].next = head[u];
head[u] = sumE;
}
int get_id(int u,char c) {
if(s[u] == 'A') return c == 'B' ? u * 2 : u * 2 + 1;
if(s[u] == 'B') return c == 'A' ? u * 2 : u * 2 + 1;
if(s[u] == 'C') return c == 'A' ? u * 2 : u * 2 + 1;
}
char get_ch(int u) {
if(s[u / 2] == 'A') return (u & 1) ? 'C' : 'B';
if(s[u / 2] == 'B') return (u & 1) ? 'C' : 'A';
if(s[u / 2] == 'C') return (u & 1) ? 'B' : 'A';
}
int sta[MAXN],top,dfn[MAXN],low[MAXN],idx,col[MAXN],tot,instack[MAXN];
vector<int> ver[MAXN];
void tarjan(int u) {
sta[++top] = u;
dfn[u] = low[u] = ++idx;
instack[u] = 1;
for(int i = head[u] ; i ; i = E[i].next) {
int v = E[i].to;
if(instack[v] == 1) {
low[u] = min(low[u],dfn[v]);
}
else if(!dfn[v]) {
tarjan(v);
low[u] = min(low[u],low[v]);
}
}
if(low[u] == dfn[u]) {
++tot;
while(1) {
int x = sta[top--];
col[x] = tot;
ver[tot].pb(x);
instack[x] = 2;
if(x == u) break;
}
}
}
bool check() {
memset(head,0,sizeof(head));
sumE = 0;
for(int i = 1 ; i <= M ; ++i) {
if(c[0][i][1] == s[u[i]]) continue;
if(c[1][i][1] == s[v[i]]) {
int x = get_id(u[i],c[0][i][1]);
add(x,x ^ 1);
}
else {
int x = get_id(u[i],c[0][i][1]),y = get_id(v[i],c[1][i][1]);
add(x,y);add(y ^ 1,x ^ 1);
}
}
for(int i = 1 ; i <= tot ; ++i) ver[i].clear();
memset(sta,0,sizeof(sta));top = 0;
memset(dfn,0,sizeof(dfn));idx = 0;
memset(low,0,sizeof(low));
memset(col,0,sizeof(col));tot = 0;
memset(instack,0,sizeof(instack));
for(int i = 2 ; i <= N * 2 + 1; ++i) {
if(!dfn[i]) tarjan(i);
}
for(int i = 2 ; i <= N * 2 + 1 ; i += 2) {
if(col[i] == col[i ^ 1]) return false;
}
memset(L,0,sizeof(L));
for(int i = 1 ; i <= tot ; ++i) {
for(auto k : ver[i]) {
if(!L[k / 2]) {
L[k / 2] = get_ch(k);
}
}
}
return true;
}
bool dfs(int dep) {
if(dep > N) {
if(check()) return true;
return false;
}
if(s[dep] != 'x') {return dfs(dep + 1);}
else {
for(int i = 0 ; i <= 2 ; ++i) {
s[dep] = 'A' + i;
if(dfs(dep + 1)) return true;
}
}
return false;
}
void Init() {
scanf("%d%d",&N,&D);
scanf("%s",s + 1);
for(int i = 1 ; i <= N ; ++i) {
if(s[i] != 'x') s[i] = s[i] - 'a' + 'A';
}
scanf("%d",&M);
for(int i = 1 ; i <= M ; ++i) {
scanf("%d%s%d%s",&u[i],c[0][i] + 1,&v[i],c[1][i] + 1);
}
}
void Solve() {
if(!dfs(1)) {puts("-1");return;}
for(int i = 1 ; i <= N ; ++i) {
putchar(L[i]);
}
putchar('\n');
}
int main() {
#ifdef ivorysi
freopen("f1.in","r",stdin);
#endif
Init();
Solve();
}

【LOJ】 #2305. 「NOI2017」游戏的更多相关文章

  1. loj #2305. 「NOI2017」游戏

    #2305. 「NOI2017」游戏 题目描述 小 L 计划进行 nnn 场游戏,每场游戏使用一张地图,小 L 会选择一辆车在该地图上完成游戏. 小 L 的赛车有三辆,分别用大写字母 AAA.BBB. ...

  2. loj#2305. 「NOI2017」游戏 2-sat

    链接 https://loj.ac/problem/2305 https://www.luogu.org/problemnew/show/P3825 思路 3-sat神马的就不要想了,NP问题 除去x ...

  3. LOJ_2305_「NOI2017」游戏 _2-sat

    LOJ_2305_「NOI2017」游戏 _2-sat 题意: 给你一个长度为n的字符串S,其中第i个字符为a表示第i个地图只能用B,C两种赛车,为b表示第i个地图只能用A,C两种赛车,为c表示第i个 ...

  4. 「NOI2017」游戏

    「NOI2017」游戏 题目描述 小 L 计划进行 \(n\) 场游戏,每场游戏使用一张地图,小 L 会选择一辆车在该地图上完成游戏. 小 L 的赛车有三辆,分别用大写字母 \(A\).\(B\).\ ...

  5. LOJ2305 「NOI2017」游戏

    「NOI2017」游戏 题目背景 狂野飙车是小 L 最喜欢的游戏.与其他业余玩家不同的是,小 L 在玩游戏之余,还精于研究游戏的设计,因此他有着与众不同的游戏策略. 题目描述 小 L 计划进行$n$场 ...

  6. 「NOI2017」游戏 解题报告

    「NOI2017」游戏 \(d\)这么小,你考虑直接对\(d\)个东西暴力 枚举\(x\)为\(a\)或\(b\)(\(c\)就不用了,因为\(a,b\)已经包含\(c\))了,剩下的就是个\(2-s ...

  7. LOJ 2304 「NOI2017」泳池——思路+DP+常系数线性齐次递推

    题目:https://loj.ac/problem/2304 看了各种题解…… \( dp[i][j] \) 表示有 i 列.第 j 行及以下默认合法,第 j+1 行至少有一个非法格子的概率,满足最大 ...

  8. LOJ 2303 「NOI2017」蚯蚓排队——链表+哈希表

    题目:https://loj.ac/problem/2303 想到合并的时候可以只考虑接口附近的50个,但不太会分析复杂度,而且没有清楚地想到用哈希值对应个数. 看了题解才会…… 一直想用 splay ...

  9. LOJ 2302 「NOI2017」整数——压位线段树

    题目:https://loj.ac/problem/2302 压30位,a最多落在两个位置上,拆成两次操作. 该位置加了 a 之后,如果要进位或者借位,查询一下连续一段 0 / 1 ,修改掉,再在含有 ...

随机推荐

  1. Java基础-IO流对象之转换流(InputStreamReader与OutoutStreamWriter)

    Java基础-IO流对象之转换流(InputStreamReader与OutoutStreamWriter) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.转换流概述 我们之前 ...

  2. jQuery中使用attribute,prop获取,设置input的checked值

    1.prop方法获取.设置checked属性 当input控件checkbox设置了checked属性时,无论checked=”“或 checked=”checked”,$(obj).prop(“ch ...

  3. ShareRepository

    文件共享下载链接: 1:关于模拟器的配置附件http://pan.baidu.com/s/1jGFqfh8 原文地址:http://www.cnblogs.com/killerlegend/p/382 ...

  4. 如何利用mount命令挂载另一台服务器上的目录

    文件服务器(被挂载机):192.168.1.100 操作机(挂载到机):192.168.1.200 也就是说,你在操作机上进行的操作,实际上都到文件服务器上去了: 1. 开启NFS服务: 在文件服务器 ...

  5. 张鑫旭:Promise异步编程模式

    参考文章: http://www.zhangxinxu.com/wordpress/2014/02/es6-javascript-promise-%E6%84%9F%E6%80%A7%E8%AE%A4 ...

  6. php strcmp()函数

    <? $str = "LAMP"; $str1 = "LAMPBrother"; $strc = strcmp($str,$str1); switch ( ...

  7. OpenCV LIBTIFF_4.0 link errors

    以前用Caffe用的好好的,今天重装后居然报了很多这样的错误 /usr/lib/libopencv_highgui.so.' 1> /usr/lib/libopencv_highgui.so.' ...

  8. UNIX环境高级编程 第5章 标准I/O库

    本章是关于C语言标准I/O库的,之所以在UNIX类系统的编程中会介绍C语言标准库,主要是因为UNIX和C之间具有密不可分的关系.由于UNIX系统存在很多实现,而每个实现都有自己的标准I/O库,为了统一 ...

  9. C++ Primer 5th 第14章 重载运算与类型转换

    当运算符作用域类类型的对象时,可以通过运算符重载来重新定义该运算符的含义.重载运算符的意义在于我们和用户能够更简洁的书写和更方便的使用代码. 基本概念 重载的运算符是具有特殊名字的函数:函数名由关键词 ...

  10. jQuery和Prototype的兼容性和冲突的五种解决方法

    第一种情况:先加载Prototype,再加载jQuery方法一:jQuery 库和它的所有插件都是在jQuery名字空间内的,包括全局变量也是保存在jQuery 名字空间内的. 使用jQuery.no ...