2011-05-17 119 views
2

我現在有一個Windows窗體應用程序,我想創建一個新線程並在另一個接受輸入的類上運行一個方法。C#中的線程問題

例如

public partial class Form1: Form { 
    SerialPort serialInput; 
    // I want to create a new thread that will pass the parameter serialInput into the method 
    // SMSListener on another class and run the method contionously on the background. 
} 

class SMS 
{ 
    public void SMSListener(SerialPort serial1) 
    { 
     serial1.DataReceived += port_DataRecieved; 
    } 

    private void port_DataRecieved(object sender, SerialDataReceivedEventArgs e) 
    { 
     // Other codes 
    } 
} 

如何在C#中執行此?我在網上看到了很多例子,他們中的大多數都在同一個類上運行方法,沒有參數,但沒有一個適合我的要求。

+2

看一看[BackgroundWorker的類(http://msdn.microsoft.com/en-us/library/system.componentmodel.backgroundworker.aspx) – digEmAll 2011-05-17 08:35:30

+0

已經嘗試過,但還是搞清楚如何得到我想要的結果。 – abduls85 2011-05-17 08:43:25

回答

2

我不是多線程方面的專家,但就我所知,您只能在接受對象參數並返回void的方法上啓動線程。因此,爲了實現這一目標對你的問題(不要拍我失望,如果有一個更好的辦法!)我會做類似

public partial class Form1: Form { 
    SerialPort serialInput; 
    // I want to create a new thread that will pass the parameter serialInput into the method 
    // SMSListener on another class and run the method contionously on the background. 
    SMS sms = new SMS(); 
    Thread t = new Thread(sms.SMSListenerUntyped); 
    t.Start(serialInput); 
} 

class SMS 
{ 
    public void SMSListenerUntyped(object serial1) { 
     if (serial1 is SerialPort) //Check if the parameter is correctly typed. 
      this.SMSListener(serial1 as SerialPort); 
     else 
      throw new ArgumentException(); 
    } 

    public void SMSListener(SerialPort serial1) 
    { 
     serial1.DataReceived += port_DataRecieved; 
    } 

    private void port_DataRecieved(object sender, SerialDataReceivedEventArgs e) 
    { 
     // Other code. 
    } 
+0

非常感謝。有效。 – abduls85 2011-05-17 08:59:46

+0

非常歡迎。很高興我能幫上忙! – Nikhil 2011-05-17 09:04:43

4

也許Background Worker可以幫到你嗎?
這很難理解你的目標。

public class Runner 
{ 
    private readonly BackgroundWorker _worker = new BackgroundWorker(); 

    public Runner() 
    { 
     _worker.DoWork += WorkerDoWork; 
    } 

    public void RunMe(int payload) 
    { 
     _worker.RunWorkerAsync(payload); 
    } 

    static void WorkerDoWork(object sender, DoWorkEventArgs e) 
    { 
     var worker = sender as BackgroundWorker; 

     while (true) 
     { 
      if (worker.CancellationPending) 
      { 
       e.Cancel = true; 
       break; 
      } 

      // Work 
      System.Threading.Thread.Sleep((int)e.Argument); 
     } 
    } 
} 
+0

我已經試過Backgroundworker,但我仍然沒有想出如何讓它工作以實現我想要的結果。基本上我想從我的winform類中運行一個新的線程,它將參數serialInput傳遞到SMS類方法SMSListener中。 – abduls85 2011-05-17 08:41:22

+0

好吧,爲什麼你需要傳入SMSListener類實例?分享國家?這可能會導致交叉線程問題。請澄清一下! – 2011-05-17 08:43:04

+0

難道你想要一個線程讀取數據,然後將它放入一個隊列中供主線程使用?即**生產者/消費者模式**?在這種情況下,背景工人顯然是不夠的。 [看看這裏](http://stackoverflow.com/questions/1371249/c-producer-consumer-pattern)關於生產者/消費者的討論。 – 2011-05-17 08:53:12

0

如何只直接使用線程池用匿名方法讓你訪問你周圍的當地人?

public void OnButtonClick(object sender, EventArgs e) 
    { 
     SerialPort serialInput = this.SerialInput; 
     System.Threading.ThreadPool.QueueUserWorkItem(delegate 
     { 
      SmsListener listener = new SmsListener(serialInput); 
     }); 
    }