none
想請問一下用「Visual Studio」直接執行程式和做成「安裝檔」後有執行何差別嗎? RRS feed

  • 問題

  • 我現在遇到一個問題是:
    我現在透過Visual Studio直接執行程式,結果都沒有任何的錯誤發生…都可以正常的執行…
    但是現在我製作成安裝檔後,安裝完後執行…就會跑出錯誤了…
    錯誤情況分別有:
    1.會跑出System.ObjectDisposedException的問題,有上去看了一下這問題大多發生在使用已Disposed的物件…但為何用VS執行時就沒有出現這樣的問題。
    2.會直接關閉程式,連問題錯誤都沒有出現。
    以上電腦是出現在二台不同的電腦上面。

    更奇怪的另一個問題就是…我再分別把安裝檔安裝到另外三台電腦上執行都沒有問題…不會跑出錯誤也不會直接關閉程式…

    ps..這5台作業系統都為xp版
    唯一最大的不同就是…有問題的那二台電腦為單核,其它三台都為雙核…在規格上明顯的差異就在這而以了…
    不知道電腦規格會有任何問題產生嗎?
    有問題的電腦也有試著重灌,結果問題還是一樣。

    程式主要用到的東西有:
    多執行緒(執行緒的暫停我是使用Interrupt,我也有改過用Abort來測試,但那二台的問題還是存在)
    ManualResetEvent
    與Rs232進行通訊
    2009年12月4日 上午 06:46

解答

  • ObjectDisposedException 通常是因為你的程式在關閉的時後, 又剛好有Invoke的程序產生, 這個錯誤通常看運氣. 因為要剛好在Invoke時關掉才會遇到
    通常這種多執行緒的程式我會做兩件事
    (1) 把 Thread執行個體的IsBackground屬性設為True , 這樣就不需去呼叫 Abort
    (2) 如果你一定要呼叫 Abort, 請在呼叫的地方, 要Try Catch 攔截 ThreadAbortException 這個錯誤. 請參考 [Thread. Abort 方法 ]
    (3) 在你程式中用於讓執行緒變更控制項的方法內, 用 Try Ctach 欄截 ObjectDisposedException , 以防止你關閉程式時, 物件已被釋放但程式還沒關完前仍然試圖存取已被釋放的物件.

    你可以參考以下文章的說明
    http://www.dotblogs.com.tw/billchung/archive/2009/04/04/7851.aspx


    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?
    • 已標示為解答 justinwu 2009年12月5日 上午 12:50
    2009年12月4日 上午 07:22
    版主

所有回覆

  • ObjectDisposedException 通常是因為你的程式在關閉的時後, 又剛好有Invoke的程序產生, 這個錯誤通常看運氣. 因為要剛好在Invoke時關掉才會遇到
    通常這種多執行緒的程式我會做兩件事
    (1) 把 Thread執行個體的IsBackground屬性設為True , 這樣就不需去呼叫 Abort
    (2) 如果你一定要呼叫 Abort, 請在呼叫的地方, 要Try Catch 攔截 ThreadAbortException 這個錯誤. 請參考 [Thread. Abort 方法 ]
    (3) 在你程式中用於讓執行緒變更控制項的方法內, 用 Try Ctach 欄截 ObjectDisposedException , 以防止你關閉程式時, 物件已被釋放但程式還沒關完前仍然試圖存取已被釋放的物件.

    你可以參考以下文章的說明
    http://www.dotblogs.com.tw/billchung/archive/2009/04/04/7851.aspx


    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?
    • 已標示為解答 justinwu 2009年12月5日 上午 12:50
    2009年12月4日 上午 07:22
    版主
  • ObjectDisposedException 通常是因為你的程式在關閉的時後, 又剛好有Invoke的程序產生, 這個錯誤通常看運氣. 因為要剛好在Invoke時關掉才會遇到
    通常這種多執行緒的程式我會做兩件事
    (1) 把 Thread執行個體的IsBackground屬性設為True , 這樣就不需去呼叫 Abort
    (2) 如果你一定要呼叫 Abort, 請在呼叫的地方, 要Try Catch 攔截 ThreadAbortException 這個錯誤. 請參考 [Thread. Abort 方法 ]
    (3) 在你程式中用於讓執行緒變更控制項的方法內, 用 Try Ctach 欄截 ObjectDisposedException , 以防止你關閉程式時, 物件已被釋放但程式還沒關完前仍然試圖存取已被釋放的物件.

    你可以參考以下文章的說明
    http://www.dotblogs.com.tw/billchung/archive/2009/04/04/7851.aspx


    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?

    嗯  請問大大

    我很好奇 「您提及的  把 Thread執行個體的IsBackground屬性設為True , 這樣就不需去呼叫 Abort 」
    是為什麼呢?   另  常常 Abort 都會關不掉執行緒
    或者 關掉之後 卻無法再次開啟 真是怪怪的
    2009年12月4日 上午 10:24
  • 因為當 Thread的IsBackground 屬性設為True時會被當成背景執行緒, 此時在你的主執行緒關閉的時候就會自動把背景執行緒關掉.
    呼叫Abort停不了的狀況我是沒遇過, 猜測可能是使用 Abort的程序不正確, 例如程式可能會先把主執行緒都關掉才呼叫Abort, 這樣就會呼叫不到.
    關於執行緒的文件可以參考  MSDN文件庫  [.NET Framework 開發人員手冊 執行緒和執行緒處理 ]
    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?
    2009年12月4日 下午 01:10
    版主

  • 錯誤情況分別有:
    1.會跑出System.ObjectDisposedException的問題,有上去看了一下這問題大多發生在使用已Disposed的物件…但為何用VS執行時就沒有出現這樣的問題。
    2.會直接關閉程式,連問題錯誤都沒有出現。
    以上電腦是出現在二台不同的電腦上面。


    justinwu 大大您好:

    1. 通常這個阿 我都是用  Try 去把錯誤處理起來 或者是 您可以試試看 應該在IDE環境下的即時運算視窗應該可以看到有類似的錯誤出現???  有嗎 還是沒有呢??
    2. 這個 我以前在BCB 常常會遇到 不過 VB 比較少哩?  您有用到 API 這種東西嗎?

    我在VB上面常常遇到他會關不掉 O_Oa  雖然確定都有 Nothing 了 但就算泡過去了 下去Run他就死掉了所以 會不會是您有放掉Thread然後又啟動Thread 造成的呢  ^_^
    2009年12月4日 下午 01:16
  • 原來是Invoke所導致的…
    不過我發現系統效能真的也有差…
    因為系統效能慢的可能會導致所要呼叫的還沒產生或者已關閉了,所以常會出現問題…
    很感謝Bill chung大大…看來我在Inovke的地方還要多研究一下了…
    2009年12月5日 上午 12:52
  • 我想在請問一下…
    以下是我的程式…

    宣告

    Dim 進度表單 As Progress
    Dim 提示字串 As String
    Dim 傳送期間錯誤 As System.Text.StringBuilder = Nothing

    Private Delegate Sub 委派更新()
    Private Delegate Sub 委派顯示錯誤訊息()
    Private Delegate Sub 委派關閉()

    Private Sub 提示視窗(ByVal 最大值 As Object)
        進度表單 = New Progress(1, True)
        進度表單.SetMax(CInt(最大值))
        進度表單.SetContent(提示字串)
        進度表單.ShowDialog()
    End Sub

    Private Sub 無暫停提示視窗(ByVal 最大值 As Object)
        進度表單 = New Progress(1, False)
        進度表單.SetMax(CInt(最大值))
        進度表單.SetContent(提示字串)
        進度表單.ShowDialog()
    End Sub

    Private Sub 進行更新訊息()
    Try
        Dim 委派 As New 委派更新(AddressOf 更新提示訊息)
        進度表單.Invoke(委派)
    Catch ex As ObjectDisposedException
    End Try
    End Sub

    Private Sub 進行顯示錯誤訊息()
    Try
        Dim 委派 As New 委派顯示錯誤訊息(AddressOf 錯誤結束訊息)
        進度表單.Invoke(委派)
    Catch ex As ObjectDisposedException
    End Try
    End Sub

    Private Sub 進行關閉視窗()
    Try
        Dim 委派 As New 委派關閉(AddressOf 關閉視窗)
        進度表單.Invoke(委派)
    Catch ex As ObjectDisposedException
    End Try
    End Sub


    呼叫流程:
    1.建立視窗執行緒
    Dim 參數執行緒 As New ParameterizedThreadStart(AddressOf 無暫停提示視窗)
    Dim 執行緒提示視窗 As New Thread(參數執行緒)

    2.更改視窗訊息執行緒
    傳送期間錯誤 = New System.Text.StringBuilder
    執行緒提示視窗.Start(染程集合.Length + 1)

    3.關閉視窗執行緒
    進行關閉視窗()

    我現在主要有這三個動作…
    而我常在2或3的地方在呼叫Invoke時會出現"視窗代碼尚未建立,無法使用Invoke"…而它跳出來的錯誤訊息則是(InvailedOpertaionException)
    故用ObjectDisposedException來Catch也無法抓到…
    請問這樣子我應該如何解決…

    我在想應該是我視窗還未建立好後就更新訊息或者就關閉視窗了…因為都是不同的執行緒是否有可能是這樣的原因呢?
    那我要如何來解決…
    2009年12月5日 上午 02:31
  • 改用非同步乎叫呢? (BeginInvoke)

    ms-help://MS.MSDNQTR.v90.cht/dv_fxadvance/html/38a345ca-6963-4436-9608-5c9defef9c64.htm
    使用委派非同步設計程式

    委派 (Delegate) 可讓您以非同步方式呼叫同步方法。同步呼叫委派時,Invoke 方法會在目前的執行緒上直接呼叫目標方法。如果呼叫 BeginInvoke 方法,則 Common Language Runtime (CLR) 會將要求放進佇列,並立即傳回給呼叫端。在執行緒集區的執行緒上,隨即以非同步方式呼叫目標方法。送出要求的原始執行緒可與目標方法無限制地持續平行執行。如果在 BeginInvoke 方法的呼叫中指定了回呼 (Callback) 方法,則當目標方法結束時,即會呼叫此回呼方法。在此回呼方法中,EndInvoke 方法會取得傳回值和任何輸入/輸出或僅能輸出的參數。如果在呼叫 BeginInvoke 時未指定任何回呼方法,則可以從稱為 BeginInvoke 的執行緒呼叫 EndInvoke

    另外建議你把 VS2008 所附的 samples
    Application Samples\Multithread\MultiThread.sln

    第三個按鈕跟你要的差不多,你可以先跑此程式,連續觸發多個執行緒測看看。


    論壇是網友平等互助 保證解答請至 微軟技術支援服務
    提問時,錯誤情境描述與錯誤訊息很重要,情境描述包含你做了什麼,預期的結果與實際發生的結果。一個最爛的問法範例:「我的電腦電腦怎麼不能開機?」誰知道你家是不是沒電還是你根本找不到電源鈕。
    2009年12月5日 上午 04:46
  • 一個題外話, 你的程式該不會真的用中文寫吧  ? 雖然系統上允許, 但最好不要這樣寫, 因為會出什麼包很難預料.
    通常發生不可避免的延遲問題, 要不就在關鍵處用Sleep等待,或用WaitHadle去控制, 要不就是使用Try Ctach去把InvaliedOperationException排除.
    這要依實際狀況測試才能得出比較清楚的結果.

    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?
    2009年12月5日 上午 04:46
    版主
  • 可以請問一下…vs2008的sample在那邊可以下載的到呢??
    另外我現在全都改成用BeginInvoke來做了…但問題還都是一直存在的說…
    而且我真的發現…在VS執行跑出ObjectDisposedException的機率真的可以說是沒有…所以我跟本沒有辦法得知是那一行的什麼程式所導致問題產生…
    而真的在cpu較慢的情況下…在使用Invoke感覺會比較容易出錯…
    而且每次在安裝完畢之後,就會跑出即時偵錯的視窗出來,然後進去vs偵錯又不會出現是那一行…
    不知道有什麼辦法可以解決的嗎…
    我已經被這錯誤快搞瘋了…希望可以指點一下…@@…
    感謝不盡…○rz...
    2009年12月7日 上午 02:40
  • 如果你沒變更安裝目錄的話,預設位置:
    C:\Program Files\Microsoft Visual Studio 9.0\Samples\1028\VBSamples.zip
    論壇是網友平等互助 保證解答請至 微軟技術支援服務
    提問時,錯誤情境描述與錯誤訊息很重要,情境描述包含你做了什麼,預期的結果與實際發生的結果。一個最爛的問法範例:「我的電腦電腦怎麼不能開機?」誰知道你家是不是沒電還是你根本找不到電源鈕。
    2009年12月7日 上午 05:44

  • 嗯嗯 其實您這個問題我也有遇到 我也無法解決

    不過 有一個地方您可以試試看

    我一開始的時候是這樣寫得

    Private Delegate Sub 委派(byval ID as byte , byval OB as Object )

    這樣我可以傳不同的參數進去用  Select Case ID  去區分用哪個控制項去接
    可是阿 我也會一直出現InvailedOpertaionException錯誤訊息  不過這個可以用Try  去包掉喔..
    出現錯誤的地方 有時有有時不會(但實際上我每個控制項都是獨立的  這樣是想要練習) 至於原因我也不曉得哩



    所以阿 我就改成項您下面這樣的寫法了、  每個控項用自己的委派
    Private Delegate Sub 委派更新()
    Private Delegate Sub 委派顯示錯誤訊息()
    Private Delegate Sub 委派關閉()
    但卻發現  這次還是會出現InvailedOpertaionException錯誤訊息 而且這次關不掉  Try 也包不掉


    所以萬一真的很急急急急急急急急  那您可以試試看小弟的作法 :D



    2009年12月7日 上午 07:11
  • 你是在哪個位置攔截這個Exception ?
    試著這樣用用看
                  Try
                    Me.Invoke(d, New Object() {lMax_MSG_UID})
                Catch exp As ObjectDisposedException
                    '也許出現ObjectDisposedException時也會要處理其它事情, 例如把Thread給強制關閉
                Catch ex As Exception
                                 MessageBox.Show(ex.ToString, "Invoke Error", MessageBoxButtons.OK, MessageBoxIcon.Error, MessageBoxDefaultButton.Button1, 0, False)
                End Try

    學而不思則罔, 思而不學則殆.
    如果你一直都看不懂、不想學習看懂、抗拒看懂MSDN Library的話,那你最好放棄想要寫好程式這件事
    如果你自私地不肯回饋與分享,那別人為何要花時間回答你的問題?
    2009年12月7日 上午 10:27
    版主