Je travaille actuellement sur un projet qui nécessite le traitement de beaucoup de données, j'ai donc décidé de créer un formulaire Windows informant l'utilisateur que le traitement est en cours. Bien sûr, je dois utiliser un autre fil. Mais j'ai besoin d'exécuter ce formulaire Windows plusieurs fois (pas en même temps mais ça démarre bien la première fois et pas bien la seconde), je dois avoir une méthode qui démarre le thread et une autre qui l'arrête ainsi qu'une étiquette qui affichera des choses différentes selon le nombre de boucles exécutées dans une méthode qui est dans un autre thread (c'est délicat ^^).

J'ai beaucoup lu sur les threads mais je n'ai toujours pas trouvé comment le faire. Un peu de code que j'ai fait:

 public partial class Progress : Form
{

    Thread thr = null;

    public Progress()
    {
        InitializeComponent();
        try
        { 
             thr = new Thread(() => this.ShowDialog());
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message);
        }
    }
    public void Start()
    {
        thr.Start();           
        //this.ShowDialog();
    }

    public void Stop()
    {
        thr.Abort();
        thr.Join();
        //this.Close();
    }

Et je veux utiliser quelque chose comme ça, comment puis-je le faire?

other class {
  Progress t = new Progress();
  t.Start();
  firstFunction();
  SecondBigFunction(t);
  threeFunction();
  t.Stop();
}

SecondBigFunction(Thread t){
  while(list.lenght > 0){
    // Do somework
    t.labelToChange += 1;
  }
}

Je vous remercie.

1
caraLinq 23 nov. 2017 à 11:19

4 réponses

Meilleure réponse

Je ne suis pas sûr mais cela peut vous aider.

labeltoChange.Invoke((MethodInvoker)(() => labeltoChange.Text+=1));
3
CanFil 23 nov. 2017 à 08:28

Vous pouvez utiliser la classe backgroundworker pour accomplir votre tâche

private BackgroundWorker bg1 = new BackgroundWorker();
 bg1.DoWork += bg1_DoWork;

 private void bg1_DoWork(object sender, DoWorkEventArgs e)
        {
           //the function you want to execute
        }

De la même manière, vous pouvez définir divers travailleurs de fond avec des fonctions différentes dans chacun d'eux.

Et enfin appeler les travailleurs d'arrière-plan dans l'ordre dans lequel vous voulez que les fonctions soient exécutées (toutes ces fonctions s'exécuteront simultanément).

4
hustlecoder 23 nov. 2017 à 08:40

Normalement, tout le travail de l'interface utilisateur doit être effectué sur le même thread. Donc, essayer de lancer un formulaire sur un thread séparé ne causera normalement que des problèmes.

À tout le moins, vous devrez utiliser Invoke, qui utilisera le thread d'interface utilisateur pour mettre à jour le contrôle. Cela signifie donc effectivement que vous n'utilisez qu'un seul thread.

Il est possible de le faire, pour plus de détails, vous devriez voir ceci; Dans WinForms, plusieurs threads sont-ils possibles dans l'interface utilisateur?

Et ça; Plusieurs threads d'interface utilisateur - Winforms

La meilleure pratique consiste à placer les calculs «durs» dans un thread de travail en arrière-plan, puis à mettre à jour l'interface utilisateur lorsque vous avez terminé.

Cet article donne un exemple; https://www.codeproject.com/Articles/99143/ BackgroundWorker-Class-Sample-for-Beginners

0
jason.kaisersmith 23 nov. 2017 à 08:42
labeltoChange.Invoke((MethodInvoker)(() => labeltoChange.Text+=1));

Cette méthode est un bon moyen, c'est juste que lorsque vous faites labeltoChange.Text+=1 vous incrémentez le nombre ne faites pas d'addition.

Si vous souhaitez ajouter à la zone de texte, utilisez ceci:

labeltoChange.Invoke((MethodInvoker)(() => Convert.ToInt32(labeltoChange.Text) + 1));
0
Barr J 23 nov. 2017 à 08:59
47450600