Domanda

Sono sicuro che un'interfaccia utente reattiva è qualcosa a cui tutti aspirano e il modo consigliato per fare cose è utilizzare BackgroundWorker per questo.

Trovi facile lavorare con ?Lo usi spesso?Oppure disponi di strutture proprie per attività lunghe e processi di reporting.

Ho scoperto che lo sto utilizzando parecchio e utilizzo anche i suoi delegati ovunque abbia bisogno di una sorta di resoconto dei progressi.

È stato utile?

Soluzione

La programmazione multithread è difficile da comprendere all'inizio (e i veterani continuano a fallire a volte) e BackgroundWorker la rende un po' più semplice da usare.Mi piace il fatto che BackgroundWorker abbia funzionalità facili da implementare ma ancora più facili da implementare erroneamente in modo sottile, come la cancellazione.Lo uso se ho e ho bisogno di un aggiornamento sullo stato di avanzamento, così posso visualizzare una barra di avanzamento significativa.

In caso contrario, utilizzo un thread (o prendo in prestito da ThreadPool), perché non ho bisogno di tutte le funzionalità di BackgroundWorker e sono sufficientemente esperto con i thread per avviare un thread e attendere che si interrompa.

Per quanto riguarda i delegati per compiti non correlati, utilizzo quelli delle classi Thread, come plain void ThreadStart(), oppure ne creo uno mio.

Altri suggerimenti

BackgroundWorker rende le cose molto più semplici.Una cosa che ho trovato nel modo più duro è che Backgroundworker stesso ha affinità di thread anche se dovrebbe nascondere il problema di cambio di thread.Non passa automaticamente al thread dell'interfaccia utente in ogni caso.È necessario crearlo ed eseguirlo dal thread dell'interfaccia utente affinché il cambio di thread avvenga correttamente.

Lo uso abbastanza spesso per attività come l'indicazione dello stato di avanzamento e il caricamento/elaborazione dei dati in background.
Recentemente ho trovato un caso d'uso che non è supportato immediatamente.È "Attività ignorabile".Comunque Patric Smacchia se ne è uscito bello soluzione.

L'ho usato una volta e ne sono rimasto abbastanza soddisfatto.Spesso non c'è bisogno di un "grande" multithreading, ma solo di 2 Thread (UI e Worker), e funziona davvero bene senza doversi preoccupare troppo della logica di threading sottostante.

@Gulzar Grazie per questa informazione:È necessario crearlo ed eseguirlo dal thread dell'interfaccia utente affinché il cambio di thread avvenga correttamente.

Una cosa a cui prestare attenzione quando si utilizza un lavoratore in background che ho trovato è la gestione delle eccezioni.

Se viene generata un'eccezione sul processo asincrono, non genererà un'eccezione al thread principale, il processo terminerà e l'evento BackgroundWorker RunWorkerCompleted verrà attivato con l'errore nascosto in RunWorkerCompletedEventArgs.Error.

Mi piace il fatto che BackgroundWorker abbia funzionalità facili da implementare ma ancora più facili da implementare erroneamente in modo sottile, come la cancellazione.

Il mio problema più grande con la classe del lavoratore in background è che non c'è davvero modo di sapere quando il lavoratore ha terminato a causa della cancellazione.BackgroundWorker non espone il thread che utilizza, quindi non è possibile utilizzare le tecniche standard per sincronizzare la terminazione del thread (join e così via).Inoltre, non puoi semplicemente attendere in un ciclo sul thread dell'interfaccia utente che termini perché l'evento RunWorkerCompleted non verrà mai attivato.L'hack che ho sempre dovuto usare è semplicemente impostare un flag e quindi avviare un timer che continuerà a controllare la fine dell'operazione in background.Ma è molto complicato e complica la logica aziendale.

Quindi è fantastico finché non è necessario supportare la cancellazione deterministica.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top