2013-06-04 15 views
5

Sto lavorando su un algoritmo di partizionamento grafico (nodi e vertici).scrittura di più thread sulla stessa booleana

Uso più thread per provare ad identificare determinate regioni all'interno del grafico.

Una volta che un nodo è stato identificato come parte di una regione, ho impostato un valore boolean marked su true per l'oggetto nodo.

Più thread possono tentare di contrassegnare lo stesso nodo allo stesso tempo.

Attualmente utilizzo la sincronizzazione per garantire che non accada nulla di brutto.

Tuttavia, poiché I mai leggere il valore di contrassegnato fino a dopo che tutti i thread hanno terminato l'elaborazione. Sarebbe possibile per me sbarazzarsi del codice di sincronizzazione? In altre parole, qualcosa può andare storto quando si scrive contemporaneamente su una variabile booleana?

+0

è segnato sempre impostato su false quando è stato impostato su true? – berry120

+0

no. appena impostato su true –

risposta

3

qualcosa può andare storto quando si scrive contemporaneamente su una variabile booleana?

Sì e no. Certamente il valore risultante non sarà in qualche modo corrotto, ma sarà non deterministico su quale degli aggiornamenti viene impostato sul campo e quando questi aggiornamenti sono visti da altri thread - se non del tutto.

Se ci sono più thread che prendono decisioni usando il valore di questo booleano, è necessario fornire a un certo punto la sincronizzazione della memoria. Rendere il campo volatile costa pochissimo e, a meno che non si abbia la prova che si tratta di un problema di prestazioni, non avere il campo essere volatile è probabilmente un'ottimizzazione prematura. Se si stanno confrontando e impostando, si consiglia un AtomicBoolean che include uno volatile boolean e fornisce metodi di livello superiore come compareAndSet(...).

0

No. Se l'ordine delle scritture su quella variabile non ha importanza.

+1

Il problema è che le scritture potrebbero * non * essere mai osservabili dai thread del lettore. – assylias

+0

@assylias Anche se "Non ho mai letto il valore di contrassegnato come dopo che tutti i thread hanno terminato l'elaborazione"? Puoi spiegare? –

+0

Il fatto che il thread di scrittura abbia risolto il suo lavoro non significa che le modifiche apportate siano state pubblicate correttamente e possano essere lette da un altro thread. – assylias

2

In teoria no, ma non mi dispiacerebbe dichiarare la variabile volatile. La parola chiave volatile garantisce l'accesso atomico.

(a condizione che l'ordine delle operazioni di scrittura non importa e tutte le letture si verificano dopo tutte le scritture.)

+2

Non si tratta di accesso atomico che avviene sempre con un 'booleano' a meno che non si stia verificando un test e si esegua un'operazione da cui' volatile' non ti salva. Riguarda l'ordine delle operazioni e la visibilità della memoria. – Gray

+0

A meno che non ci sia una sincronizzazione corretta, è possibile che un thread del lettore legga "false" anche se un thread writer imposta il valore booleano su "true". C'è * un * problema di visibilità in ciò che l'OP descrive. – assylias

2

No, niente poteva andare storto quando più thread scrivono allo stesso valore booleano, ma non ci può essere un problema di leggere il valore (anche molto tempo) successivamente in un thread diverso. È necessario contrassegnare almeno le variabili come volatile per evitare il problema.

1

Come altri hanno già detto, non vi è alcun rischio di corruzione o valori errati per il valore booleano se si sta semplicemente tentando di impostarlo sullo stesso valore da più thread.

Tuttavia, non si può nemmeno bisogno che

non ho mai letto il valore di marcato fino a dopo tutti i fili hanno terminato l'elaborazione.

rapporto

È, ovviamente, bisogno di una sorta di barriera per sincronizzare il filo di coordinamento con i thread di lavoro (ad esempio Thread.join() o CountdownLatch o il vostro primitivo du jour) e quasi tutti quelli già fornire una accade, prima che verrà rendere tutti i tuoi segni visibili al thread del coordinatore.

Avere quel singolo punto di sincronizzazione anche accade solo per essere più conveniente che la lettura di un gran numero di volatili (e io non lo chiamerei che l'ottimizzazione prematura, semplicemente elidendo la necessità di volatili)

+0

grazie .. ha senso. (Stavo usando thread.join()) insieme all'uso di booleans volatili. Userò booleans invece di booleans volatili –

Problemi correlati