Cod sursa(job #2308248)

Utilizator shantih1Alex S Hill shantih1 Data 26 decembrie 2018 18:28:56
Problema Santa Scor 100
Compilator cpp-64 Status done
Runda Lista lui wefgef Marime 3.07 kb
#include <iostream>
#include <fstream>
#include <vector>
#include <deque>
#define nmx 45105

using namespace std;
ifstream fin("santa.in");
ofstream fout("santa.out");

int n,m,x,s,e,q,i,j,nr,pi,pf,nn,n1,sf,nrf,nttt,un,care;
int v[nmx],z[nmx],h[nmx],p[32800][17],l[17][17],drfin[nmx],drc[nmx],back[nmx],ok[nmx];
vector<int> ad[nmx],no[nmx],ptr[32800];
deque<int> dq;

int crit12(int nd,int p)
{
	h[nd]=h[p]+1;
	int mx=h[nd],f,nr=0;
	for(int j:ad[nd])
		if(j!=p)
		{
			if(h[j])	f=h[j];
			else
			{
				nr++;
				f=crit12(j, nd);
				if(care && f>=h[nd])	z[nd]=1;
				if(!care)
				{
					ok[nd]|=ok[j];
					if(f>=h[nd] && ok[j]==0)	z[j]=nd;
				}
			}
			mx=min(mx,f);
		}
	if(care && nd==1 && nr==1)	z[1]=0;
	return mx;
}
void calcul(int st,int t)
{
	if(p[st][t])	return;
	int x=st-(1<<(t-1));
	
	for(int j:ptr[x])
		if(j>1 && l[t][j])
		{
			calcul(x, j);
			if(p[x][j])	
			{	p[st][t]=j;		return;		}
		}
}
void reset(int st,int t)
{
	p[st][t]=0;
	int x=st-(1<<(t-1));
	for(int j:ptr[x])
		if(p[x][j])	reset(x,j);
}
void path()
{
	int i,j,nr=0;
	un++;
	for(i=1;i<=nn;i++)
	{
		ok[v[i]]=un;
		for(j=1;j<=nn;j++)	l[i][j]=0;
	}
	for(i=1;i<=nn;i++)
		for(int k:ad[v[i]])
			if(ok[k]==un)	l[i][h[k]]=l[h[k]][i]=1;
	
	for(i=2;i<=nn;i++)
		if(l[1][i])	p[1+(1<<(i-1))][i]=1;
	
	int x=(1<<nn)-1,y;
	if(sf)	calcul(x, sf);
	else 
		for(i=2;i<=nn;i++)
		{
			calcul(x, i);
			if(p[x][i])	sf=i, i=nn;
		}
	if(sf==0)	n1=100;
	int c=sf;
	
	while(sf)
	{
		y=p[x][sf];
		drc[++nr]=v[sf];
		x-=(1<<(sf-1));
		sf=y;
	}
	if(x)	n1=100;
	
	for(i=nr;i>=1;i--)
		if(drc[i]!=drfin[nrf])	drfin[++nrf]=drc[i];
	
	reset((1<<nn)-1, c);
	for(i=2;i<=nn;i++)	p[1+(1<<(i-1))][i]=0;
}
int main() {
	
	fin>>n>>m;
	for(i=1;i<=m;i++)
	{
		fin>>s>>e;
		ad[s].push_back(e), ad[e].push_back(s);
	}
	fin>>s>>e>>q;
 
	ok[e]=1, care=0;
	crit12(s,0);
	
	for(i=1;i<=n;i++)
		if(z[i])
		{
			dq.push_back(i);
			while(!dq.empty())
			{
				x=dq.front();
				dq.pop_front();
				for(int j:ad[x])
					if(j!=z[x] && z[j]==0)
					{
						z[j]=z[x];
						dq.push_back(j);
					}
			}
		}
	
	for(i=1;i<=n;i++)
	{
		ok[i]=0;
		if(z[i]==0)	ok[i]=++nn, back[nn]=i;
		z[i]=ok[i];
		ok[i]=0;
	}
	nttt=nn;
	
	for(i=1;i<=n;i++)
		if(z[i])
			for(int j:ad[i])
				if(z[j])	no[z[i]].push_back(z[j]);
	n=nn;
	q=z[q];
	for(i=1;i<=n;i++)
	{
		while(!ad[i].empty())	ad[i].pop_back();
		for(int j:no[i])
			ad[i].push_back(j);
		z[i]=0;
		h[i]=0;
	}
	
	care=1;
	crit12(1, 0);
	for(i=1;i<=n;i++)	h[i]=0;
 
	for(i=1;i<=32768;i++)
		for(j=0;j<=15;j++)
			if(i&(1<<j))	ptr[i].push_back(j+1);
	
	if(z[q] || q==0)
	{	fout<<"No chance\n";	return 0;	}
	
	m=n-1;
	h[q]=1;
	v[nn=1]=q;
	dq.push_back(q);
	while(!dq.empty())
	{
		x=dq.front();
		dq.pop_front();
		
		if(z[x]==1 || m==0)
		{
			sf=h[x];
			if(m==0)	sf=0;
			path();
			
			if(n1>1)
			{	fout<<"No chance\n";	return 0;	}
			n1--;
			if(m==0)	m--;
			z[x]=0;
			v[nn=1]=x;
			h[x]=1;
			dq.push_back(x);
			continue;
		}
		for(int j:ad[x])
			if(h[j]==0)
			{
				h[j]=++nn, m--;
				v[nn]=j;
				if(z[j]==0)	dq.push_front(j);
				else	dq.push_back(j), n1++;
			}
	}
	fout<<nttt<<"\n";
	for(i=1;i<=nttt;i++)
		fout<<back[drfin[i]]<<" ";
	fout<<"\n";
}