【杂题合集】其真无码邪?

杂题合集

十月份了,该开新篇了
标题党去死

P1407 [国家集训队]稳定婚姻

题目概述:

我们这里有 nCP,但是他们之间的关系可能很胃疼很白学,所以有 m 对曾经的 CP。设第 iCP 的男方为 Bi,女方为 Gi,若男 Bi 与女 Gj (ij) 曾交往过,当 BiGi 闹矛盾了,Bi 就有可能去找 Gj 寻求安慰。
比如北原春希和小木曾雪菜是 CP,但他们当产生矛盾时,北原春希会去找冬马和纱寻求安慰。
再比如说仲上真一郎和汤浅比吕美闹掰了,于是仲上真一郎去找石动乃绘寻求安慰;同时,汤浅比吕美也去找到了石动纯;这样原本的两对 CP(兄妹)就被拆开了,但是又组成了两对新的 CP我是养鸡党),我们称这样的关系是不稳定的。

简而言之,若在 BiGi 闹掰的前提下,这 2n 个人仍然能组成 nCP,那么关系 i 就是不稳定的,否则,关系 i 就是稳定的。

需要判断每对关系是不是稳定的。

真TM难概括,艹

题解

如果 CP 关系是 Unsafe 的,那么这几个人的关系一定是一个环。

以样例2为例:

image

四个人形成了一个不具稳定关系的四边形,所以两对 CP 都是不稳定的。

而样例1:

image

没有形成环,两对 CP 都是稳定的。

每一个环都是一个强连通分量,所以可以想到tarjan来求强连通分量,
然后问题就是如何建图了,不难想到可以建无向边,但是无向图没法跑这个,那考虑 CP 和前 CP 分开连边。CP 从女到男连边,前 CP 从男到女连边。为什么?考虑传递性。我们假定每次 CP 关系破裂后,男方 Bi 先去找前 CP Gj。然后像多米诺骨牌一样的传递,Gj 传递给 Bj,两人关系破裂,Bj 再去找 Gk......以此类推。

所以,当 CP 双方在同一个强连通分量中,那这对关系是不稳定的,反之稳定。

Code

点击查看代码
#include<set>
#include<string>
#include<iostream>
#include<algorithm>
#include<unordered_map>
using namespace std;
const int MAXN = 4010;
int n, m, cnt, sit, num, tot;
int head[MAXN << 1], low[MAXN << 1], dfn[MAXN << 1], belong[MAXN << 1];
bool vis[MAXN << 1];
int stk[MAXN << 1], top;
string boy[MAXN], girl[MAXN];
unordered_map< string, int > pos;
struct Edge{
int to, next;
}e[MAXN * MAXN];
inline void Add(int u, int v){
e[++cnt].to = v;
e[cnt].next = head[u];
head[u] = cnt;
}
void Tarjan(int u){
low[u] = dfn[u] = ++num;
vis[u] = true;
stk[++top] = u;
for(register int i = head[u]; i; i = e[i].next){
int v = e[i].to;
if(!dfn[v]){
Tarjan(v);
low[u] = min(low[u], low[v]);
}
else if(vis[v]) low[u] = min(low[u], dfn[v]);
}
if(low[u] == dfn[u]){
++tot;
int t;
do{
t = stk[top--];
vis[t] = false;
belong[t] = tot;
}while(t != u);
}
}
int main(){
ios :: sync_with_stdio(0);
cin.tie(0), cout.tie(0);
cin >> n;
for(register int i = 1; i <= n; i++){
int u = ++sit, v = ++sit;
cin >> girl[i] >> boy[i];
Add(u, v);
pos[girl[i]] = u, pos[boy[i]] = v;
}
cin >> m;
for(register int i = 1; i <= m; i++){
string g, b;
cin >> g >> b;
int u = pos[g], v = pos[b];
Add(v, u);
}
for(register int i = 1; i <= sit; i++)
if(!dfn[i]) Tarjan(i);
for(register int i = 1; i <= n; i++){
int u = pos[girl[i]], v = pos[boy[i]];
if(belong[u] != belong[v]) puts("Safe");
else puts("Unsafe");
}
return 0;
}
posted @   TSTYFST  阅读(132)  评论(4编辑  收藏  举报
相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具
点击右上角即可分享
微信分享提示