IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Windows Forms Discussion :

[C# 2.0] Databind très lent de la UI ? Solution?


Sujet :

Windows Forms

  1. #1
    Candidat au Club
    Inscrit en
    Juillet 2003
    Messages
    5
    Détails du profil
    Informations forums :
    Inscription : Juillet 2003
    Messages : 5
    Points : 2
    Points
    2
    Par défaut [C# 2.0] Databind très lent de la UI ? Solution?
    Bonjour à tous,

    Je développe un application WinForm en C# 2.0.
    Le problème qui se pose me semble réellement "basique":

    J'utilise un BackGroundWorker pour récupérer les données de ma DataLayer (ex: liste de contrats). Grace au BgWorker, mon interface ne "freeze" pas et reste réactive. Le problème survient lorsque je procède au Databind de ma collection d'objets à ma UI (que ce soit un DataGridView, ListBox, ComboBox, ListView, ...).

    J'utilise le code suivant (je place bien le DisplayMember et ValueMember avant le DataSource, ce qui est sensé améliorer la rapidité du DataBind):

    grid.DisplayMember = "UCN";
    grid.ValueMember = "ContractID";
    grid.DataSource = datasource;


    Le vrai problème reste que j'ai généralement des DataSources qui contiennent de ~500 à 50.000 records. Le Databind fait alors "freezer" toute mon interface.

    J'ai trouvé de la documentation à propos de Invoke et BeginInvoke qui semblent être la piste à suivre (j'ai suivi l'exemple suivant, voir bout de code à la fin de l'article: http://www.codeproject.com/KB/cs/Asy...nvocation.aspx) mais cela n'a pas changé le fait que mon interface freeze pendant quelques secondes.

    Je m'étonne de ne pas trouver de solution évidente à mon problème, peut-être n'ai-je pas recherché sur les bons termes dans Google,...?

    Que me conseillez-vous pour arriver à obtenir une interface "réactive", j'aimerais afficher un progressBar pendant que mon composant UI soit Databindé (je le fais déjà pour des traitements non UI, ca marche très bien, le problème se pose dès qu'il y a du Databinding).

    Auriez-vous un exemple concret, ou une explication peut-être du pourquoi mon test ne marche pas...?


    J'espère que mon explication est suffisament claire.

    Merci d'avance

    Mike

    N.B.: Je me suis dit qu'avec un exemple de code ce serait plus clair:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
     
    public interface ICommand
    {
        void Execute();
    }
     
        public class GetContractListCommand : ICommand
        {
            private GetContractListDelegate m_invokeMe;
            private ListBox m_box;
            private int m_intCustmerId;
     
            // notice that the delegate is private,
            // only the command can use it.
            private delegate TList<BLL.Contract> GetContractListDelegate();
     
            public GetContractListCommand(TList<BLL.Contract> contracts,
                ListBox listBox)
            {
                m_box = listBox;
     
                // setup the delegate to call
                m_invokeMe =
                    new GetContractListDelegate(DAL.DataRepository.ContractProvider.GetAll);
            }
     
            public void Execute()
            {
                // call the method on the thread pool
                m_invokeMe.BeginInvoke(
                    this.CallBack, // callback!
                    null);
            }
     
            private void CallBack(IAsyncResult ar)
            {
                // get the Collection of Contracts as output
                TList<BLL.Contract> datasource = m_invokeMe.EndInvoke(ar);
     
                // update the ListBox a thread safe fasion!
                MethodInvoker updateListBox = delegate
                {
                    m_box.DisplayMember = "UCN";
                    m_box.ValueMember = "ContractID";
                    m_box.DataSource = datasource;
                };
     
                if (m_box.InvokeRequired)
                    m_box.Invoke(updateListBox);
                else
                    updateListBox();
            }
        }
     
        partial class PanelContracts : UserControl
    	{
            private ICommand m_GetContractListCommand;
     
    		protected WorkspaceManager m_WorkspaceSubject;
    		protected TList<BLL.Contract> m_Contracts;
     
    		public PanelContracts(WorkspaceManager workspace)
    		{		
    			InitializeComponent();
     
    			Load();
    		}
     
            private void Load()
            {
                // create a command that has all the tools to update the grid
                m_GetContractListCommand = new GetContractListCommand(
                    m_Contracts, boxContracts);
     
                // call the command in a non blocking mode.
                m_GetContractListCommand.Execute();
            }
    }

  2. #2
    AP
    AP est déconnecté
    Membre confirmé
    Avatar de AP
    Profil pro
    Inscrit en
    Avril 2002
    Messages
    480
    Détails du profil
    Informations personnelles :
    Âge : 43
    Localisation : France, Rhône (Rhône Alpes)

    Informations forums :
    Inscription : Avril 2002
    Messages : 480
    Points : 538
    Points
    538
    Par défaut
    Il faut commencer à se poser des question quand on veux charger plus de 10 000 items. En général il faut charger par morceau et utiliser des composants proposant un mode virtuel.

  3. #3
    Membre expérimenté
    Homme Profil pro
    Inscrit en
    Juillet 2007
    Messages
    1 277
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Réunion

    Informations forums :
    Inscription : Juillet 2007
    Messages : 1 277
    Points : 1 521
    Points
    1 521
    Par défaut
    Quand je dois gérer des listes de 50k items, j'utilise rarement les contrôles tout fait de .NET qui sont plutôt utiles : je préfère créer un contrôle qui Bind uniquement les données visible, ce qui est tout de même beaucoup plus rapide que de faire un bind complet comme le fait les composants .NET.

Discussions similaires

  1. BDD sur réseau très très très lent...
    Par ericain dans le forum Access
    Réponses: 12
    Dernier message: 20/02/2015, 17h17
  2. Ouverture et fermeture de base très lent...
    Par Tofdelille dans le forum Installation
    Réponses: 6
    Dernier message: 19/09/2006, 18h51
  3. [Lomboz] Editeur jsp très lent
    Par lr dans le forum Eclipse Java
    Réponses: 10
    Dernier message: 29/01/2005, 19h43
  4. SQL Server trés lent
    Par arwen dans le forum MS SQL Server
    Réponses: 18
    Dernier message: 07/11/2003, 14h45

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo