2013-08-20 8 views
6

Ho un problema dove trovo la profondità minima possibile di un grafico che implica che devo trovare la profondità massima da ciascun nodo e restituire il minimo di tutti. Ovviamente un semplice DFS da ogni nodo farà il trucco, ma quando le cose impazziscono con input estremamente grandi, DFS diventa inefficiente (limite di tempo). Ho provato a mantenere la distanza di ogni foglia sul nodo che si sta esplorando in memoria, ma ciò non ha aiutato molto.Trovare in modo efficiente la profondità di un grafico da ogni nodo

Come trovare in modo efficiente la profondità minima di un grafico molto grande. È degno di nota che il grafico in questione ha nessun ciclo.

+0

Stai cercando di trovare il [centro del grafico] (http://en.wikipedia.org/wiki/Graph_center) di un grafico ad albero non orientato? –

+0

@PeterdeRivaz Sì, qualcosa del genere –

risposta

9

Per trovare il grafico centrale/centro di un grafo ad albero non orientato si potrebbe:

  1. fare un DFS per trovare un elenco di tutti i nodi foglia O (n)
  2. eliminasse tutti questi nodi foglia dal grafico e nota durante l'eliminazione che nuovi nodi diventano nodi foglia
  3. Ripetere passaggio 2 finché il grafico viene completamente eliminato

il nodo/nodi cancellate nell'ultima fase dell'algoritmo sarà il grafico centri del tuo albero.

Ogni nodo viene eliminato una volta, quindi l'intero processo può essere eseguito in O (n).

+0

Il numero di iterazioni sarebbe quindi il valore di ritorno? Destra? –

+0

Se ci sono più nodi cancellati nell'ultima fase, la risposta sarà il numero di iterazioni. Tuttavia, se è stato eliminato un singolo nodo all'ultimo stadio, la risposta sarà il numero di iterazioni -1. (Un albero A-B sarà rimosso in 1 iterazione e avrà profondità 1, mentre un albero A sarà anche rimosso in 1 iterazione e haa profondità 0) –

+0

Mi manca qualcosa o l'ultimo nodo da eliminare sarà sempre la chiave del DFS? – tumasgiu

0

Cosa ti sembra di essere alla ricerca di è il diametro/2. Si potrebbe calcolare il diametro di un albero come qui sotto e chiamare come findDiameter(n, null), per un nodo arbitrario n dell'albero.

public findDiameter(node n, node from) returns <depth, diameter> 

    // apply recursively on all children 
    foreach child in (neighbors(n) minus from) do 
     <de, di> = findDiameter(child, n) 

    // depth of this node is 1 more than max depth of children 
    depth = 1 + max(de) 

    // max diameter either uses this node, then it is 1 + the 2 largest depths 
    // or it does not use this node, then it's the max depth of the neighbors 
    diameter = max(max(di), 1 + max(de) + oneButLargest(de)) 

Tutto quello che dovete fare è nel ciclo sopra i vicini tenere traccia del più grande diametro e le 2 profondità maggiori.

+0

dalla definizione di "diametro di un grafico" mentre leggo [qui] (http://en.wikipedia.org/wiki/Eccentricity_ (graph_theory) #Related_concepts), dubito che questo risolva il mio problema. Puoi per favore spiegare come questo si riferisce al mio problema. Grazie. –

+0

@OlayinkaSF Il diametro 'd' di un albero è la lunghezza del percorso più lungo tra due foglie. Considera il nodo centrale 'm' in quel percorso (assumendo che' d' sia pari, se 'd' è dispari, ci sono 2 nodi di questo tipo).La profondità massima da 'm' è' d/2' (la sua profondità massima deve essere trovata lungo il percorso più lungo, o avremmo una contraddizione e qualche altro percorso sarebbe più lungo). Per ogni altro nodo, la profondità massima è almeno 'd/2 + 1' (instradarla tramite' m' e quindi a una delle estremità del percorso più lungo). Quindi, 'm' è un centro grafico e il valore che si cerca è' d/2'. –

Problemi correlati