洛谷P5782 POI2001 和平委員會

2022-07-22 19:51:13 字數 1722 閱讀 1032

2-sat問題模板

先看兩道

例題:【模板】2-sat 問題

滿漢全席

在搞懂上面的題後,這題就並不難了。

最主要的就是跑tarjan和連邊。

比如說:a,b為乙個黨派,c,d為乙個黨派,且a,c有仇,那麼只能選a,d或b,c。也就是說要在a,d之間連一條邊,在b,c之間連一條邊。

上述操作完成後,tarjan跑一邊縮點,如果同乙個黨派的兩人在同乙個強連通分量裡,那麼和平委員會就不能創立。~~(別告訴我你連tarjan都不會)~~

**如下

鄰接表做法:

#includeusing

namespace

std;

vector

g[16005

];stack

s;int n,m,a,b,ind,cnt,dfn[16005],low[16005],scc[16005],opp[16005],val[16005

];bool f,vis[16005

];void tarjan(int

u)else

if(vis[v])low[u]=min(low[u],dfn[v]);

}if(low[u]==dfn[u])

while(u!=v);

}}int

main()

for(int i=1;i<=n*2;i++)if(!dfn[i])tarjan(i);

for(int i=1;i<=n*2;i+=2

) }

if(f)printf("

nie"

);

else

for(int i=1;i<=2*n;i++)if(scc[i]1?i+1:i-1])printf("

%d\n

",i);

}

前向星做法:

#includeusing

namespace

std;

struct

edgeed[

32005

];stack

s;int n,m,a,b,num,head[16005],ind,cnt,dfn[16005],low[16005],scc[16005],opp[16005],val[16005

];bool f,vis[16005

];void add(int u,int

v)void tarjan(int

u)else

if(vis[v])low[u]=min(low[u],dfn[v]);

}if(low[u]==dfn[u])

while(u!=v);

}}int

main()

for(int i=1;i<=n*2;i++)if(!dfn[i])tarjan(i);

for(int i=1;i<=n*2;i+=2

) }

if(f)printf("

nie"

);

else

for(int i=1;i<=2*n;i++)if(scc[i]1?i+1:i-1])printf("

%d\n

",i);

}

對比:鄰接表佔空間少,但比較慢;前向星佔空間多,但比較快。反正都能過

洛谷P2001 硬幣的面值

其實這道題就按照題面意思直接模擬一下就好喇!很顯然如果給定硬幣的最小值大於1則輸出 no answer 因為這樣子就無法取到1這個面值了。先證明一下這一點 如果目前狀態可取前 x xx 且當前取了乙個面額為 a aa 的硬幣,要想構成前 x a x a x a 的所有 必須僅當 x a 1 x ge...

洛谷P2001硬幣的面值

題目傳送門 真是個毒瘤題 一開始想這是乙個多重揹包板子題,於是不假思索打了上去,樣例沒過,再一看題,原來不是 又眼瞎了 於是再次認真讀題 很顯然我們可以發現 如果給定硬幣最小面額大於1,那麼就一定輸出no answer!因為首先 為1的就組成不了。接著思考,假設第i種硬幣已用最小硬幣數ans組成最大...

洛谷P2444 POI2000 病毒

二進位制病毒審查委員會最近發現了如下的規律 某些確定的二進位制串是病毒的 如果某段 中不存在任何一段病毒 那麼我們就稱這段 是安全的。現在委員會已經找出了所有的病毒 段,試問,是否存在乙個無限長的安全的二進位制 示例 例如如果為病毒 段,那麼乙個可能的無限長安全 就是010101 如果為病毒 段,那...