Description
我國的離婚率連續7年上升,今年的頭兩季,平均每天有近5000對夫婦離婚,大城市的離婚率上升最快,有研究婚姻問題的專家認爲,是與簡化離婚手續有關。 25歲的姍姍和男友談戀愛半年就結婚,結婚不到兩個月就離婚,是典型的“閃婚閃離”例子,而離婚的導火線是兩個人爭玩電腦遊戲,丈夫一氣之下,把電腦炸爛。有社會工作者就表示,80後求助個案越來越多,有些是與父母過多幹預有關。而根據民政部的統計,中國離婚五大城市首位是北京,其次是上海、深圳,廣州和廈門,那麼到底是什麼原因導致我國成爲離婚大國呢?有專家分析說,中國經濟急速發展,加上女性越來越來越獨立,另外,近年來簡化離婚手續是其中一大原因。 ——以上內容摘自第一視頻門戶 現代生活給人們施加的壓力越來越大,離婚率的不斷升高已成爲現代社會的一大問題。而其中有許許多多的個案是由婚姻中的“不安定因素”引起的。妻子與丈夫吵架後,心如絞痛,於是尋求前男友的安慰,進而夫妻矛盾激化,最終以離婚收場,類似上述的案例數不勝數。我們已知n對夫妻的婚姻狀況,稱第i對夫妻的男方爲Bi,女方爲Gi。若某男Bi與某女Gj曾經交往過(無論是大學,高中,亦或是幼兒園階段,i≠j),則當某方與其配偶(即Bi與Gi或Bj與Gj)感情出現問題時,他們有私奔的可能性。不妨設Bi和其配偶Gi感情不和,於是Bi和Gj舊情復燃,進而Bj因被戴綠帽而感到不爽,聯繫上了他的初戀情人Gk……一串串的離婚事件像多米諾骨牌一般接踵而至。若在Bi和Gi離婚的前提下,這2n個人最終依然能夠結合成n對情侶,那麼我們稱婚姻i爲不安全的,否則婚姻i就是安全的。給定所需信息,你的任務是判斷每對婚姻是否安全。
Input
第一行爲一個正整數n,表示夫妻的對數;以下n行,每行包含兩個字符串,表示這n對夫妻的姓名(先女後男),由一個空格隔開;第n+2行包含一個正整數m,表示曾經相互喜歡過的情侶對數;以下m行,每行包含兩個字符串,表示這m對相互喜歡過的情侶姓名(先女後男),由一個空格隔開。
Output
輸出文件共包含n行,第i行爲“Safe”(如果婚姻i是安全的)或“Unsafe”(如果婚姻i是不安全的)。
Sample Input
2
Melanie Ashley
Scarlett Charles
1
Scarlett Ashley
【樣例輸入2】
2
Melanie Ashley
Scarlett Charles
2
Scarlett Ashley
Melanie Charles
Sample Output
Safe
Safe
【樣例輸出2】
Unsafe
Unsafe
【數據規模和約定】
對於100%的數據,所有姓名字符串中只包含英文大小寫字母,大小寫敏感,長度不大於8,保證每對關係只在輸入文件中出現一次,輸入文件的最後m行不會出現未在之前出現過的姓名,這2n個人的姓名各不相同,1≤n≤4000,0≤m≤20000。
題解:
正解目測是tarjan找環什麼的,博客左側友鏈的一些大神應該有這道題的正解的解析。
但是目測可以用枚舉刪的邊然後找到是否有增廣路來判斷,相當於有的話那麼可以判定一個人可以匹配到另一個人的配偶。
本來想用鄰接矩陣寫來着但是發現會TLE。
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <set>
#include <map>
#include <string>
#include <queue>
using namespace std;
const int MAXN=8001;
const int MAXM=400001;
struct xx
{
int from,to,nxt;
}e[MAXM];
int head[MAXM],father[MAXN],cnt,n,m,T;
bool visit[MAXN];
bool g[MAXN][MAXN];
int match[MAXN],b[MAXN],B[MAXN];
int use[MAXN];
map <int,string> M1;
map <string,int> M2;
queue <int> Q;
inline void add(int x,int y)
{
cnt++;
e[cnt].from=x;
e[cnt].to=y;
e[cnt].nxt=head[x];
head[x]=cnt;
}
int find(int x)
{
if(x==father[x]) return x;
father[x]=find(father[x]);
return father[x];
}
bool search(int x)
{
int i;
use[x]=T;
for(i=head[x];i;i=e[i].nxt)
{
if(b[e[i].to]==x) continue;
if(!b[e[i].to])
{
b[e[i].to]=x;
return true;
}
if(use[b[e[i].to]]!=T&&search(e[i].to))
{
b[e[i].to]=x;
return true;
}
}
return false;
}
int main(int argc, char *argv[])
{
int i,j,x,y,t;
int l=0,r=0;
char s1[10],s2[10];
string p,q;
scanf("%d",&n);
for(i=1;i<=n;i++)
{
scanf("%s",s1);
scanf("%s",s2);
M1[i*2-1]=s1,M1[i<<1]=s2;
if(!M2[s1]) l++,M2[s1]=l;
if(!M2[s2]) r++,M2[s2]=r;
g[M2[s1]][M2[s2]]=1;
B[M2[s2]]=M2[s1];
}
scanf("%d",&m);
for(i=1;i<=m;i++)
{
scanf("%s",s1);
scanf("%s",s2);
if(g[M2[s1]][M2[s2]]!=1) add(M2[s1],M2[s2]);
}
for(i=1;i<=n;i++)
{
for(j=1;j<=n;j++)
b[j]=B[j];
b[i]=0;
T++;
if(search(i)) puts("Unsafe");
else puts("Safe");
g[i][i+1]=1;
}
return 0;
}