none
SerialPort 停止問題 (因為執行緒結束或應用程式要求,所以已中止I/O操作) RRS feed

  • 問題

  • Dear all,

    目前有一支程式,透過Serial Port來讀取某一外部裝置傳來的數值,

    但如果我按下停止鍵時,有時會出現 "因為執行緒結束或應用程式要求,所以已中止I/O操作。"

    這樣的訊息,附上程式碼

    爬了相關的文章,但問題還是會存在,不知哪裡需要修正?另外發現該訊息也不是每次都會有,

    感覺有時候才會出現,完全抓不到頭緒,

    請教各位先進

    Thanks.

    接收端:

    private void comport_DataReceived(Object sender, SerialDataReceivedEventArgs e)
    {
                try
                {
                    string str = (sender as SerialPort).ReadLine();
                    Display d = new Display(DisplayText);
                    this.Invoke(d, new Object[] { str });
                }
                catch (Exception ex)
                {
                    MessageBox.Show(ex.Message);
                }
    }

     關閉:

    private void btnStop_Click(object sender, EventArgs e)
    {
            try
                {
                    if (comport.IsOpen)
                    {
                        comport.DataReceived -= new SerialDataReceivedEventHandler(comport_DataReceived);                     comport.Close();
                    }
                }
                catch (Exception ex)
                {
                    throw (new Exception(ex.Message));
                }
    }


    • 已編輯 菲羽 2015年5月8日 上午 02:49
    2015年5月7日 上午 07:01

解答

  • 假設你是主管,你命令一位下屬去買便當,當你臨時決定不吃了,你應該通知這位下屬不要買便當或是告知買回來的便當如何處理,而不是直接自行中止,不然便當錢要誰出?

    多緒程式也是如此,你命令一個 SerialPort 去傳送、接收資料,你要停止時,一般慣例是:

    1. 通知該執行緒。

    2. 逾時中止該執行緒,並 catch 錯誤訊息紀錄或拋棄。

    所以當該執行緒仍在執行中,你直接中止時會有錯誤,但傳送、接收中間是有空檔的,你在空檔或執行緒跑完時結束是不會跳錯的。


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2015年5月9日 上午 09:38

所有回覆

  • 假設你是主管,你命令一位下屬去買便當,當你臨時決定不吃了,你應該通知這位下屬不要買便當或是告知買回來的便當如何處理,而不是直接自行中止,不然便當錢要誰出?

    多緒程式也是如此,你命令一個 SerialPort 去傳送、接收資料,你要停止時,一般慣例是:

    1. 通知該執行緒。

    2. 逾時中止該執行緒,並 catch 錯誤訊息紀錄或拋棄。

    所以當該執行緒仍在執行中,你直接中止時會有錯誤,但傳送、接收中間是有空檔的,你在空檔或執行緒跑完時結束是不會跳錯的。


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2015年5月9日 上午 09:38
  • 你說的沒錯,因為看起來是執行緒還沒停止,也就是還持續接收時,強制中斷引起的,

    如果 comport_DataReceived 是引發另一個執行緒去處理接收來自Com Port的資料,而且是不斷的接收,

    那麼我要如何通知該執行緒停止?

    要像一般Thread 使用 Abort、或Interrupt 這類方法?

    Thanks.你的回答



    2015年5月11日 上午 02:10
  • Thread 中止是用 abort 沒錯,但會擲出例外,所以屬於上述 2 的部分。

    1 的部分通常是用一個共用變數,例如:ThreadStop = True ,然後在 Thread 迴圈裡多檢查這個變數,若是 ThreadStop ,Exit Do/For/Sub 均可,當執行緒結束時,自然會無錯終止。

    所以應優先令其 終止 ,而不是隨意 中止 。


    不精確的問法,就會得到隨便猜的答案;自己都不肯花時間好好描述問題,又何必期望網友會認真回答?

    2015年5月11日 下午 12:52