Cod sursa(job #1474144)

Utilizator alex_ovidiunituAlex Ovidiu Nitu alex_ovidiunitu Data 21 august 2015 01:37:33
Problema Componente biconexe Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.82 kb
/*
Fie T un arbore de adâncime descoperit de parcurgerea grafului. Atunci, un nod v este punct de articulaţie dacă:
    v este rădăcina lui T şi v are doi sau mai mulţi copii
sau
    v nu este rădăcina lui T şi are un copil u în T, astfel încât nici un nod din subarborele dominat
    de u nu este conectat cu un strămoş al lui v printr-o muchie înapoi (copii lui nu pot ajunge pe altă
    cale pe un nivel superior în arborele de adâncime).
    idx[u] = timpul de descoperire a nodului u
    low[u] = min( {idx[u]} U { idx[v] : (u, v) este o muchie înapoi } U
        { low[vi] : vi copil al lui v în arborele de adâncime} )
+http://pastebin.com/AjZ1LvXj
+http://www.infoarena.ro/job_detail/236392?action=view-source
*/
#include <fstream>
#include <iostream>
#include <set>
#include <stack>
#include <vector>
#include <algorithm>
#include <bitset>
#define nmax 100015
using namespace std;
int n,m, idx[nmax], componente, low[nmax];
vector <int> v[nmax];
fstream f,g;
struct edge
{
    int nod1, nod2;
    edge ()
    {
        nod1 = nod2 = 0;
    }
    edge ( int x, int y)
    {
        nod1 = x;
        nod2 = y;
    }
    bool operator = ( edge a)
    {
        nod1 = a.nod1;
        nod2 = a.nod2;
    }
};
stack <edge> stiva;

void determina_componenta_biconexa(int x, int y)
{
    componente++;
    int folosit[nmax] = {0};
    edge muchie;
    do
    {
       muchie =  stiva.top();
        stiva.pop();
        if ( !folosit[muchie.nod1] ) g<<muchie.nod1<<" ";
        if ( !folosit[muchie.nod2] ) g<<muchie.nod2<<" ";
        folosit[muchie.nod1] = 1;
        folosit[muchie.nod2] = 1;
    }while ( muchie.nod1 != x || muchie.nod2 !=y);

    g<<'\n';
}
void DFS(int nod, int tata, int nivel)
{
    int i;
    idx[nod] = nivel;
    low [nod] = nivel;//pe ce nivel e posibil sa ma intorc

    for ( i = 0 ; i < v[nod].size() ; i++ )
    {
        if ( tata == v[nod][i])
            continue;
        if (idx[v[nod][i]] == 0) // nu am umblat pe la el
        {
            // bag muchia in arborele dfs
            edge muchie = edge(nod, v[nod][i]);
            stiva.push( muchie);

            DFS(v[nod][i], nod, nivel + 1);
            // actualizez
            low[nod] = min (low[v[nod][i]], low[nod]);
            // vad daca e punct de articulatie
            if (low[v[nod][i]] >= idx[nod])
                determina_componenta_biconexa(nod, v[nod][i]);
        }
        else
            low[nod] =  min (low[nod], low[v[nod][i]]); // posibila muchie intoarcere
    }
}
int main(void)
{
    int i,x,y;
    f.open("biconex.in",ios::in);
    g.open("biconex.out",ios::out);
    f>>n>>m;
    for (i = 1 ; i<= m ;i++)
    {
        f>>x>>y;
        v[x].push_back(y);
        v[y].push_back(x);
    }

    //!! vezi daca e conex sau nu
    g<<"         \n";
    DFS (1, 0, 1);// consider 1 radacina;
    g.seekg(0,ios::beg);
    g<<componente;
}