Chargement de la DataTable Lent Quand il est Lié à DataGridView.Source de données
J'ai cherché partout et je ne peux pas comprendre ça. Je suis en train de travailler sur un Winforms de l'INTERFACE utilisateur qui est en tirant de gros volumes de lignes que j'ai besoin d'afficher dans un DataGridView. J'ai déjà tout lu à propos de la limitation du nombre de lignes et de pagination et il n'y a absolument pas de bonne façon pour moi de le faire. Fondamentalement, je suis en train de travailler sur la TargetDataViewer de contrôle de l'Étendue des Événements Manager for SQL Server 2008 que j'ai écrit sur Codeplex.
http://extendedeventmanager.codeplex.com/
Je suis limité à ce que je peux faire en fonction de la cible et la façon dont il présente des données. Ce que j'essaie de faire est de transmettre les données qui ont été lues à partir d'une cible dans le DataGridView similaire à la façon dont Profiler, ou SQL Server Management Studio d'affichage des données de flux. J'ai réécrit beaucoup de code, et un BackgroundWorker de l'extraction de données et de traitement dans une DataTable. Si je n'ai pas mis le DataGridView.DataSource = DataTable, je peux charger 300K+ lignes de données dans la Table de données en quelques minutes, il fonctionne vraiment rapide. Dès que j'ai ajouter le DataTable à la source de données lente, presque à l'arrêt (au lieu de quelques minutes, le même 300K lignes peuvent prendre une 1/2 heure).
Je sais que le problème n'est pas de mon code de traitement, il est spécifique à être lié à la DataGridView.Source de données, et j'ai du code de cadencement pour le prouver. Je ne peux pas comprendre comment obtenir autour de cette. Pour les Performances, je peux en retard lier le contrôle à la Table de données une fois les données chargées, mais c'est vraiment une merde expérience de l'utilisateur. Je vois beaucoup de gens se plaignent du DataGridView impact sur les performances lors du chargement de données si ce n'est peut-être une limitation, je suis coincé avec? Des idées?
Non, j'ai SqlDataReader c'est en tirant un non-liés au schéma XML du document pour chaque ligne. Puis-je avoir le code qui est l'analyse de ce document XML dans un objet[] qui est passée comme params à la LoadRow() la méthode.
OriginalL'auteur Jonathan Kehayias | 2009-07-17
Vous devez vous connecter pour publier un commentaire.
Penser à ce qui se passe lorsque vous remplissez un indépendant
DataTable
avec une ligne à partir d'unDataReader
: UnDataRow
est créé, rempli à partir de laDataReader
, et ajouté à laRows
collection. Ensuite, lorsque vous créez la liaison, laDataGridView
extrait des données de la table et s'appuie le point de vue sur l'écran.Ce qui se passe lorsque vous remplissez un
DataTable
dont la liaison à laDataGridView
est-il activé? Un gâchis de la gestion des événements. Chaque fois que vous modifiez une propriété liée, la propriété a changé événement est levé et le contrôle lié aux poignées. Ce n'est pas passe de 300 000 fois, ça se passe de 300 000 fois pour chaque colonne.Que si vous désactivez cette fonction, et ne mettre à jour le contrôle de temps en temps? Regardez cette méthode:
Vous devez appeler ResetBindings pour forcer la mise à jour de la borne de contrôle. Cela prend du temps, parce que vous ne pouvez pas contourner le coût de construction de
DataGridViewRow
objets, mais de prendre les événements est une amélioration significative. Sur ma machine, si je remplir un 10-colonne, 10000 ligneDataTable
qui est lié à unDataGridView
, il faut 2900 millisecondes. Si je laisse de liaison de données éteint tout le temps, il prend 155 millisecondes. Si je réinitialise les liaisons tous les 500 lignes, il faut 840 millisecondes.Bien sûr, si j'étais le remplissage de 300 000 de lignes de la table, je n'aurais pas réinitialiser les liaisons tous les 500 lignes; je le ferais probablement une fois à l'500-ligne de marque, puis l'éteindre jusqu'à ce que l'opération est terminée. Mais même si vous faites cela, vous devez appeler
Application.DoEvents
chaque tellement souvent, de sorte que l'INTERFACE utilisateur de réagir aux événements.Modifier
Jamais l'esprit que peu sur
Application.DoEvents
; vous n'avez pas besoin de faire cela si vous êtes le remplissage de la table dans une tâche d'arrière-plan.Mais vous avez besoin pour vous assurer que vous êtes à la réinitialisation de l'liaisons dans l'
BackgroundWorker
'sProgressChanged
gestionnaire d'événements, et non pas dans leDoWork
méthode. Et vous allez faire l'expérience d'un monde de souffrance, si vous permettez à l'utilisateur de modifier données dans leDataGridView
alors que vous êtes le remplissage de sa source de données sur un autre thread.Heureux de l'entendre. Je pense que vous êtes toujours susceptible d'avoir beaucoup de mal avec un contrôle d'INTERFACE utilisateur lié à une source de données avec 300K enregistrements en elle, cependant. Cela semble être une quantité folle de données pour essayer de gérer avec le DataGridView limitée d'outils.
OriginalL'auteur Robert Rossney