J'ai un joli programme C#, mais le traitement des octets reçus en série est beaucoup trop lent. Et je pense que je peux peut-être résoudre cela en utilisant un travailleur de fond, mais je n'ai aucune expérience avec elle et toutes mes tentatives antérieures ont échoué.C# Comment implémenter un arrière-plan dans cette configuration?
private void serial_DataReceived(object sender, SerialDataReceivedEventArgs e)
{
rxBuffer += serial.ReadExisting(); // add new bytes to the string 'rxBuffer'
this.Invoke(new EventHandler(serialReceived));
}
private void serialReceived(object s, EventArgs e)
{
while (rxBuffer.Length > 0) // keep processing bytes until the string is empty
{
// textBox1.Text += rxBuffer[0];
byte b = Convert.ToByte(rxBuffer[0]);
string hexValue = b.ToString("X");
rxBuffer = rxBuffer.Remove(0, 1); // removes the 'captured' byte from the string
.....
lots of code
Cette boucle while représente essentiellement 75% de mon programme entier. Les octets incomming
contoll Les éléments d'interface utilisateur, ils peuvent stocker ou lire des fichiers texte et envoyer des octets sur le port série, il peut tout simplement faire à peu près tout.
Ce système fonctionne mais il est beaucoup trop lent. Donc, je pense que déplacer la boucle while dans un fond d'écran pourrait le résoudre. Comment est-ce que je peux implémenter un ouvrier d'arrière-plan dans la configuration de code actuelle?
Toutes mes tentatives ont jusqu'ici échoué.
EDIT: Je veux ajouter quelque chose que je viens de commenter ci-dessous. Je pensais que serial_DataReceived
serait appelé avec chaque octet unique. Il se passe un délai de 2 ms entre 2 octets reçus suivant dans mon application. ReadExisting()
retourne parfois plus de 1 octet. Il y a donc un certain retard dans l'événement en série. Je l'ai eu aussi en Qt mais cela n'a jamais été un problème, je pense que c'est une caractéristique de recevoir des cordes entières à la fois.
Personnellement, je pense que le invoke()
rend tout lent, mais je n'ai aucune expérience antérieure avec C# donc je devine juste, de toute façon je suis ouvert à toutes les solutions.
Voici un lien qui indique comment utiliser l'arrière-plan; https://stackoverflow.com/questions/6481304/how-to-use-a-backgroundworker –
Quelle est la raison derrière l'utilisation de 'ReadExisting'? surtout si vous êtes réellement intéressé par les octets? =! [SerialPort.Read] (https://msdn.microsoft.com/fr-fr/library/ms143549 (v = vs.110) .aspx) lit les octets directement dans un tampon. Il semble que tout le traitement de chaîne est en fait le processus lent, si vous le mettez en arrière-plan, il ne sera pas plus rapide. Puisque vous avez déjà implémenté l'événement 'serial_DataReceived', votre processus est déjà sur un thread d'arrière-plan. –
Que faites-vous dans 'beaucoup de code' de sorte qu'il nécessite un appel' Invoke'? L'appel le rend probablement si lent (et mon ancienne supposition sur le traitement des chaînes est fausse) –