Cod sursa(job #467317)

Utilizator freak93Adrian Budau freak93 Data 28 iunie 2010 14:07:20
Problema Andrei Scor 50
Compilator cpp Status done
Runda Stelele Informaticii 2010, clasele X-XII, Ziua 2 Marime 2.84 kb
#include<fstream>
#include<vector>
#include<queue>
#include<stack>

using namespace std;

const char iname[]="andrei.in";
const char oname[]="andrei.out";
const int maxn=200005;

ifstream f(iname);
ofstream g(oname);

int n,m,i,j,edges[maxn][3];
vector<int> E[maxn];

int low_link[maxn],ind[maxn],indecs,ctc,s[maxn],value[maxn],x,grade[maxn];

queue<int> Q;
stack<int> S;
vector<int> CTC[maxn];
//good around here

void tarjan(int x)
{
    low_link[x]=ind[x]=++indecs;
    S.push(x);
    for(vector<int>::iterator it=E[x].begin();it!=E[x].end();++it)
        if(low_link[*it]==0)
            tarjan(*it),low_link[x]=min(low_link[x],low_link[*it]);
        else
            if(ind[*it]>0)
                low_link[x]=min(low_link[x],low_link[*it]);
    if(ind[x]==low_link[x])
    {
        ++ctc;
        int node;
        do
        {
            CTC[ctc].push_back(node=S.top());
            ind[node]=-1;
            S.pop();
            s[node]=ctc;
        }while(node!=x);
    }
}//merge

int main()
{
    f>>n>>m;
    for(i=1;i<=m;++i)
    {
        f>>edges[i][0]>>edges[i][1]>>edges[i][2];
        if(edges[i][2]==2)
            E[edges[i][0]].push_back(edges[i][1]),E[edges[i][1]].push_back(edges[i][0]),
            E[n+edges[i][0]].push_back(n+edges[i][1]),E[n+edges[i][1]].push_back(edges[i][0]+n);
        else
            if(edges[i][2]==0)
                E[edges[i][0]].push_back(edges[i][1]+n),E[edges[i][1]].push_back(n+edges[i][0]);
            else
                E[n+edges[i][0]].push_back(edges[i][1]),E[n+edges[i][1]].push_back(edges[i][0]);
    }
    for(i=1;i<=2*n;++i)
        if(ind[i]==0)
            tarjan(i);

    for(i=1;i<=n;++i)
        {
            for(vector<int>::iterator it=E[i].begin();it!=E[i].end();++it)
                if(s[i]!=s[*it])
                    ++grade[s[*it]];
            for(vector<int>::iterator it=E[n+i].begin();it!=E[n+i].end();++it)
                if(s[n+i]!=s[*it])
                    ++grade[s[*it]];
        }
    for(i=1;i<=ctc;++i)
        if(grade[i]==0)
            Q.push(i);//bun
    for(i=1;i<=2*n;++i)
        value[i]=-1;
    while(!Q.empty())
    {
        x=Q.front();
        Q.pop();
        for(vector<int>::iterator it=CTC[x].begin();it!=CTC[x].end();++it)
            for(vector<int>::iterator jt=E[*it].begin();jt!=E[*it].end();++jt)
                if(s[*it]!=s[*jt])
                {
                    --grade[s[*jt]];
                    if(grade[s[*jt]]==0)
                        Q.push(*jt);
                }

        for(vector<int>::iterator it=CTC[x].begin();it!=CTC[x].end();++it)
            if(value[*it]==-1)
            {
                if((*it)>n)
                    value[*it]=1,value[(*it)-n]=0;
                else
                    value[*it]=1,value[(*it)+n]=0;
            }
    }//corect pana aici

    for(i=1;i<=n;++i)
        g<<value[i]<<" ";
    g<<"\n";//crek bag citire parsata
}