38 votes

Quel est le problème avec appeler Invoke, indépendamment d'InvokeRequired?

J'ai vu l'installation commune de la croix-threading accès à une interface graphique de contrôle, tel que discuté ici: http://stackoverflow.com/questions/571706/shortest-way-to-write-a-thread-safe-access-method-to-a-windows-forms-control

Toutes les visites du site web, j'ai trouvé décrire une chose semblable.

Cependant, pourquoi avons-nous besoin de vérifier InvokeRequired? Ne peut-on pas appeler Appeler directement?

Je suppose que la réponse est non, alors, ma vraie question est "pourquoi"?

30voto

Marc Gravell Points 482669

De non-threads UI nous ne pouvons pas toucher à l'INTERFACE utilisateur très mauvaises choses peuvent se produire, puisque la contrôles de l'affinité de thread. Donc, à partir d'un non-thread de l'INTERFACE utilisateur, nous devons (au minimum) appel Invoke ou BeginInvoke.

Pour UI-fils, cependant, - nous ne voulons appeler Invoke beaucoup de temps; le problème est que si vous êtes déjà sur le thread de l'INTERFACE utilisateur, il a encore la surcharge inutile d'envoyer un message à la forme de la pompe et de sa transformation.

En réalité, dans la plupart des threading code vous savez vous s'attendre à une méthode spécifique pour être appelé sur un non-thread d'INTERFACE utilisateur, de sorte que dans ces cas, il n'y a pas de charge supplémentaire: appelez - Invoke.

3voto

Brian Rasmussen Points 68853

InvokeRequired vous indique essentiellement si vous exécutez sur le bon thread ou non. Si vous n'êtes pas sur le bon thread, vous devez marshaler la tâche sur le bon thread sinon vous ne le faites pas. D'où la nécessité du chèque.

1voto

JonStonecash Points 354

Le problème est que les contrôles d'interface utilisateur graphique ont une obligation d'exécution de code sur le même thread que celui qui a été utilisé pour instancier l'interface graphique de contrôle peut accéder à l'interface graphique de contrôle. Les raisons de cette exigence est liée à la façon dont Windows est architecturé. Il suffit de dire, il serait très difficile de changer cela.

Le InvokeRequired vérifie l'identité de l'exécution de fil à l'encontre de l'identité de la thread. Si elles sont identiques, le code peut interagir librement avec le contrôle. Si non, le code doit regrouper les données en face de l'actuel thread le thread. C'est une opération coûteuse et lente et doit être évitée si possible. Votre code ne fonctionnera que si vous avez toujours invoquer, et il se peut que vous ne verrez pas les performances, mais ce scénario va être de plus en plus commun que les systèmes multi-core en utilisation. Il est préférable de ne pas créer un code "noeuds" qui doivent être annulée plus tard.

1voto

Dmitry Fedorkov Points 1680

Si vous essayez d'appeler avant la création du handle de fenêtre (par exemple, appel à partir du constructeur de formulaire), vous obtiendrez un InvalidOperationException . Donc, dans le cas général InvokeRequired vérification est absolument nécessaire.

Consultez MSDN pour plus de détails.

0voto

NileshChauhan Points 3126

L'Invoke va appeler le code via Delegate et non directement ce qui serait coûteux.

Il est rentable d'appeler Invoke uniquement lorsque cela est nécessaire. Par conséquent, InvokeRequired est utilisé pour savoir si l'appel est effectué à partir du même thread ou d'un autre thread?

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X