2011-11-05 32 views
10

Sto compilando un datagridview da un datatable.C# molto lento che popola il datagridview

Mentre compongo le colonne e le righe, lo formo anche allo stesso tempo, perché la visualizzazione di datagrid viene caricata molto lentamente, è possibile ovviare a questo problema?

+0

Avete un esempio di codice della formattazione. Quanti dati stai caricando nella griglia? usi una fonte dati paginata o carichi tutto nella rete? – Ivo

+0

Puoi pubblicare il codice che usi per popolare DatagridView? Hai legato il datagridView con il datatable o fai scorrere il datatable e inserisci il record in DatagridView? – aleroot

risposta

3

Quando si utilizza una vista datagrid per visualizzare i dati da dataabse, si dovrebbe sempre pensare di utilizzare una strategia per limitare i risultati impostati e mostrare i record solo quando l'utente li vede realmente. Questo è chiamato a volte modalità virtuale, o paging dei dati. Ho ottenuto un example of this strategy for wpf, ma c'è qualcosa anche per Winforms. Dai un'occhiata anche a questa domanda: Winform DataGridview incredibly slow compared to MS Access Grid Penso che sia correlato anche al tuo problema.

+0

D'accordo, quando qualcuno parla della lentezza di un datagrid di solito si tratta delle migliaia di righe che vengono lette per la visualizzazione di sole 10 righe. Assicurati di leggere i dati impaginati. (aka: paging dei dati) – detay

+1

@detay yeah la magia di avere una griglia veloce non è la velocità con cui la si riempie ma evitando di riempirla: D –

4

È possibile verificare la proprietà di DataGridView - AutoSizeColumnsMode Ho scoperto che se cambio la modalità da AllCells a DisplayedCells la prestazione è diversa. Spero che questo ti possa aiutare.

10

Oltre a occuparsi di AutoSizeColumnsMode, assicurarsi che le singole colonne abbiano la proprietà AutoSizeMode impostata su un valore diverso da tutte le celle.

Ho anche trovato necessario usare

SendMessage(dg.Handle, WM_SETREDRAW, false, 0); // before 

// updates to datagridview here... 

SendMessage(dg.Handle, WM_SETREDRAW, true, 0); // after 
+1

Modifica di AutoSizeColumnsMode su None prima di aggiornare l'origine dati, quindi impostarla su Tutto dopo il L'origine dati è stata impostata ha ridotto il tempo di caricamento per me da diversi minuti a meno di un secondo. – KevenDenen

6

stavo prendendo circa 2-4 minuti per caricare 1-2K righe. Ho modificato la proprietà di ridimensionamento automatico e ora è ridotta a secondi, probabilmente 10-20. L'ho eseguito subito prima del ciclo di creazione della mia riga per assicurarmi che avesse ottenuto tutte le colonne.

foreach (DataGridViewColumn c in thisGrid.Columns) 
{ 
    c.AutoSizeMode = DataGridViewAutoSizeColumnMode.None; 
} 
2

Le regole di un vecchio mio stupido: - EVITARE DataTable, ben noto per essere inefficicient - Evitare l'uso preallocazione di righe [ "Grid" .Rowcount + "Grid" .AddRange() + .. ] (~ 5 volte più lento di "Grid" ADD()) - Considera che un DataGridView è associato a "tuo schermo": es. LOAD con poche schermate di dati. - Ho applicato questi semplici fatti e posso "caricare" un "file stupido" di 420.000 righe con 159 colonne in 15 secondi. (~ 200 MB).

0

Ho una buona prestazione di DataGridView. L'aggiunta di diverse centinaia di righe richiede circa 200ms. Ecco quello che faccio:

virtual = true - utilizzando una griglia dati virtualizzato vista sembra rendere l'intero processo più veloce. Ricorda solo di implementare correttamente logViewGrid_CellValueNeeded.

Un'altra cosa da fare è disabilitare temporaneamente gli eventi di layout quando si aggiungono dati all'elenco vincolato. Provate a fare:

logViewGrid.SuspendLayout(); 
// add data, perform some operations on grid view 
logViewGrid.ResumeLayout(false); 

Ho anche avuto un problema con filari lenti colorazione; il mio metodo per farlo era impostare lo stile ciascuno cellule a parte, in questo modo:

gridViewInstance.Rows[currentRow].Cells[cellIndex].Style.BackColor = val; 

Invece, mi sono recato per:

gridViewInstance.Rows[currentRow].DefaultCellStyle.BackColor = val; 

Il che, per 30 colonne, mi ha dato significativo aumento di velocità in quella parte del codice.

0

Ho eseguito alcuni test in un programma in cui carico 5000 righe con 6 colonne e ogni cella viene caricata con il numero di riga solo per avere alcuni dati. Ho quindi usato il cronometro per testare ogni approccio. Ho caricato il dataviewgrid, l'ho disabilitato e caricato, poi l'ho abilitato, nascosto, caricato e mostrato, e suspendlayout e resumelayoutout. L'ho trovato nascondendolo e caricandolo e quindi mostrandolo era molto più veloce nei miei test. Sono stati necessari: .91 secondi per caricare solo .91 secondi per sospendereLayout, caricare, ripristinareLayout .25 secondi per disabilitare, caricare e riattivare la griglia .19 secondi per nascondere, caricare e mostrare la griglia.

Sono d'accordo sul fatto che si dovrebbe evitare di caricare ciò di cui non si ha bisogno, ma si pensava che questo test avrebbe aiutato.

6

Con questo sarà datagridview veloce come java JTable :)

public static class ExtensionMethods 
{ 
    public static void DoubleBuffered(this DataGridView dgv, bool setting) 
    { 
     Type dgvType = dgv.GetType(); 
     PropertyInfo pi = dgvType.GetProperty("DoubleBuffered", 
      BindingFlags.Instance | BindingFlags.NonPublic); 
     pi.SetValue(dgv, setting, null); 
    } 
} 

ExtensionMethods.DoubleBuffered(dataGridView1, true);