Il problema della miniera d'oro può essere risolto utilizzando divide et impera?

2

C'è un noto problema di programmazione dinamica che si chiama "miniera d'oro". Hai una griglia n x n, ciascuna delle quali contiene un certo valore di monete. Inizi a partire dal basso a sinistra e puoi solo muoverti a destra, in alto o diagonalmente in alto e a destra. L'obiettivo del tuo algoritmo è determinare il percorso attraverso la miniera che massimizza la quantità di oro che raccogli.

Una soluzione di esempio: link

È possibile risolvere questo problema usando un approccio divide-and-conquer usando O (n) space o meno, usando ancora O (n ^ 2) tempo?

Il mio primo sospetto è che puoi dividere la griglia in quadranti in modo ricorsivo, trovare il percorso migliore in ciascuno di quei quadranti, quindi in qualche modo unire il risultato alla fine per ottenere il percorso migliore attraverso l'intera faccenda. Usando solo lo spazio O (n) è possibile memorizzare i percorsi in ogni quadrante, poiché il percorso più lungo attraverso ciascuno di essi è 2n - 2. Ma facendo ciò "dimentichi" altre celle che valgono punti che non sono stati scelti, e la risposta fornita da quell'algoritmo ha la tendenza ad essere errata. Se guardiamo tutte le celle in ogni fase di unione nel tentativo di ricordare quelle scartate (che impiega n ^ 2 volte), allora la soluzione alla relazione di ricorrenza per il tempo di esecuzione diventa n ^ 2 log n invece di n ^ 2, tramite il teorema principale. La fase di unione deve essere eseguita in O (n log n) o O (n).

Lo spazio richiesto qui è il kicker più del tempo richiesto.

    
posta NmdMystery 07.10.2016 - 20:31
fonte

2 risposte

0

Si scopre che c'era una risposta.

L'algoritmo per farlo funziona come segue:

Dividi la griglia in quadranti. Inizia a risolvere i valori DP per il quadrante in alto a destra, quindi in alto a sinistra, quindi in basso a destra. Quando lo fai, salva solo i dati DP per le celle che delimitano gli altri quadranti e sbarazzati di tutti gli altri spazi di lavoro.

La ricorsione effettiva inizia quindi nel quadrante in basso a sinistra. Questo sottoproblema sembra identico al problema più grande - divide il quadrante in quattro e fa di nuovo la stessa cosa.

Quando arrivi a una griglia di dimensioni 2x2, risolvi normalmente usando l'approccio DP. Questo è un tempo costante. Quando hai finito di seguire il percorso attraverso quella griglia, saprai anche quale quadrante stai entrando dopo perché hai tenuto in memoria le celle di confine e puoi fare una scelta. Ora, risolvi il percorso attraverso quel quadrante, e poi l'ultimo.

Il percorso percorre solo tre quadranti a causa dei vincoli sul gruppo di mosse. Quindi stiamo solo risolvendo tre sotto-problemi, non quattro. È per questo che la ricorrenza semplifica ancora a O (n ^ 2):

T (n) = 3T (n / 2) + O (n ^ 2)

L'O (n ^ 2) è la prima parte dell'algoritmo, in cui si ottengono le celle DP confinanti. Il 3T (n / 2) è la soluzione dei tre quadranti. Questo appartiene al caso nel Teorema Master dove log_b (a) < c, quindi T (n) = O (n ^ c) = O (n ^ 2).

La ricorrenza per lo spazio è questa:

T (n) = T (n / 2) + n

Questo appartiene allo stesso caso nel Teorema Master come ricorrenza per il tempo di esecuzione. Lo spazio totale utilizzato è O (n).

    
risposta data 14.10.2016 - 01:13
fonte
1

C'è un problema con il tuo approccio divide et impera di dividere la griglia in quattro quadranti: le soluzioni per i quadranti non sono indipendenti l'una dall'altra. E non riesci a trovare la soluzione ottimale combinando le sub-soluzioni localmente ottimali di ogni quadrante.

+---+---+
| C | D |
+---+---+
| A | B |
+---+---+

Qui, D può essere calcolato indipendentemente. Tuttavia, la soluzione per C dipende da D, B dipende da D e A dipende da B, C, D. (La dipendenza è determinata dalla raggiungibilità.)

Risolvere il problema per un quadrante non significa che troviamo il percorso migliore. Invece, dobbiamo trovare il miglior percorso per ogni cella ai loro bordi sinistro e inferiore, poiché non sappiamo dove il miglior percorso entrerà in quel quadrante.

Le esatte complessità spaziali dipendono da ciò che stiamo cercando di calcolare:

  • il percorso migliore: questo richiederà O (n) spazio per record per un quadrante con bordi n-lunghi.
  • il valore del percorso migliore: questo richiederà O (1) spazio per record.

Farò un passo falso per questa discussione e denoterò lo spazio richiesto con s (n). Quindi, la soluzione di un quadrante richiede lo spazio O (n · s (n)) per i record del margine sinistro e inferiore.

La complessità spaziale totale dell'algoritmo viene quindi fornita attraverso la relazione di ricorrenza T (n) = 4 · T (n / 4) + O (n · s (n)). Questo darebbe T (n) & in; Θ (n · s (n)) per entrambe le opzioni per s (n).

Annotare l'algoritmo sarebbe estremamente noioso, quindi non lo farò qui. Tuttavia, la firma del risolutore ricorsivo potrebbe essere:

solve_quadrant(grid: int[n, n],
               x_start: int, x_end: int,
               y_start: int, y_end: int,
               upper_edge: Result[],
               right_edge: Result[])
               -> (left_edge: Result[], lower_edge: Result[])

E l'invocazione di livello superiore sarebbe:

solve(grid: int[n, n]) -> Result {
  left_edge, lower_edge = solve_quadrant(grid, 0, n, 0, n, {0, ..., 0}, {0, ..., 0})
  return lower_edge[0] // assuming bottom-left is at coordinate (0, 0)
}

Poiché l'algoritmo divide et impera deve soddisfare le stesse dipendenze dei dati di una soluzione di programmazione dinamica, è improbabile che superi la soluzione DP con la complessità dello spazio Θ (n · s (n)). In effetti, la complessità del "divide & conquistare "algo e algo DP sono equivalenti, poiché fanno la stessa cosa allo stesso modo - solo la strategia per la suddivisione è diversa. Tuttavia, la soluzione DP è molto più semplice da programmare poiché non deve considerare quante più condizioni di bordo.

    
risposta data 08.10.2016 - 16:51
fonte

Leggi altre domande sui tag