2012-04-04 19 views
1

Ich habe einen Thread in einer Funktion, die die Live-Überwachung starten, es öffnet im Grunde die serielle Schnittstelle und kontinuierlich Daten von der seriellen Schnittstelle lesen. Wenn ich diesen Thread beenden muss, wie soll ich das tun? Denn wenn ich nicht den laufenden Thread beende, der den spezifischen seriellen Port geöffnet hat und Daten gelesen hat. Wenn ich es schließe und die Funktion erneut aufruft. Derselbe serielle Port kann nicht geöffnet werden. Ich vermute, dass die serielle Schnittstelle nicht richtig geschlossen ist und immer noch in einem separaten Thread läuft. Also denke ich, dass ich diesen Thread beenden muss, um den gleichen seriellen Port das nächste Mal wieder zu öffnen. Hat jemand eine Idee, wie man das erreicht?Threading in winform - Compact .NET Framework 3.5

Ich habe einige Forum gesehen, dass Thread.Abort() gefährlich ist zu verwenden. Es sollte nur in letzter Instanz verwendet werden.

Danke für jede Hilfe.

Charles

+0

Sie müssen Ihren Code so strukturieren, dass der Thread elegant stirbt. Wenn Sie etwas Code (den Code, den der Thread ausführt) posten, wäre es einfacher, eine hilfreiche Antwort zu geben. –

Antwort

2

Im Allgemeinen entwerfen Sie die Methode, die im Hintergrundthread ausgeführt wird, um auf Löschungsanforderungen zu warten. Dies kann so einfach wie ein boolescher Wert sein:

//this simply provides a synchronized reference wrapper for the Boolean, 
//and prevents trying to "un-cancel" 
public class ThreadStatus 
{ 
    private bool cancelled; 

    private object syncObj = new Object(); 

    public void Cancel() {lock(syncObj){cancelled = true;}} 

    public bool IsCancelPending{get{lock(syncObj){return cancelled;}}} 
} 

public void RunListener(object status) 
{ 
    var threadStatus = (ThreadStatus)status; 

    var listener = new SerialPort("COM1"); 

    listener.Open(); 

    //this will loop until we cancel it, the port closes, 
    //or DoSomethingWithData indicates we should get out 
    while(!status.IsCancelPending 
     && listener.IsOpen 
     && DoSomethingWithData(listener.ReadExisting()) 
     Thread.Yield(); //avoid burning the CPU when there isn't anything for this thread 

    listener.Dispose(); 
} 

... 

Thread backgroundThread = new Thread(RunListener); 
ThreadStatus status = new ThreadStatus(); 
backgroundThread.Start(status); 

... 

//when you need to get out... 
//signal the thread to stop looping 
status.Cancel(); 
//and block this thread until the background thread ends normally. 
backgroundThread.Join() 
2

Zuerst denken Sie Thread in ihm haben und alle Threads schließen Sie alle von ihnen zu Hintergrund-Threads festgelegt sollten, bevor Sie sie starten, dann werden sie automatisch, wenn die Anwendung beendet wird geschlossen.

Und dann versuchen, auf diese Weise:

Thread somethread = new Thread(...); 
someThread.IsBackground = true; 
someThread.Start(...); 

http://msdn.microsoft.com/en-us/library/aa457093.aspx

+0

+1 - Ich würde mehr hinzufügen, wenn es erlaubt wäre. Es ist der einfachste Weg. Es ist nur ein serieller Port Thread lesen, also wen interessiert es, wenn das Betriebssystem es beim Herunterfahren zerstört! Das OS kann im Gegensatz zu Benutzercode leicht mit Schleifen und/oder blockierten Threads umgehen. Das Bummeln mit booleschen Stopp-Flags oder das periodische Überprüfen von Abbruchzuständen ist am besten überhaupt nicht möglich. Wenn der Thread nicht explizit beendet werden muss, tun Sie es nicht! –

+0

Wird der Thread in diesem Formular automatisch beendet, sobald das Formular geschlossen wird? –

+0

@ Charles-Ja, es beendet alle Threads einmal beim Beenden der Anwendung. – coder

1

Verwenden Sie ein boolean-Flag auf false gesetzt anfänglich finden und wenn Sie Ihren Faden Sie es auf true gesetzt beenden möchten. Anscheinend muss Ihre Haupt-Thread-Schleife dieses Flag überwachen. Wenn es sieht, dass es sich auf wahr ändert, dann ist es ziemlich dein Polling, schließe den Port und verlasse die Haupt-Thread-Schleife.

Ihre Hauptschleife könnte wie folgt aussehen:

OpenPort(); 
while (!_Quit) 
{ 
    ... check if some data arrived 
    if (!_Quit) 
    { 
     ... process data 
    } 
} 
ClosePort(); 

Je nachdem, wie Sie neue Daten warten, bis Sie den Einsatz von Ereignissen machen möchten (ManualResetEvent oder AutoResetEvent), um deinen Thread aufwachen, wenn Sie wollen es zu beenden.

Verwandte Themen