2013-07-02 33 views
0

所以,我一直在使用在WeakReferences一段代碼。我知道共同的.IsAlive比賽條件,所以我沒有使用它。我基本上是這樣的:看似無害的WeakReference訪問的NullReference?

WeakReference lastString=new WeakReference(null); 
public override string ToString() 
{ 
    if(lastString!=null) 
    { 
    var s=lastString.Target as string; //error here 
    if(s!=null) 
    { 
     return s; 
    } 
    } 
    var str=base.ToString(); 
    lastString=new WeakReference(str); 
    return str; 
} 

不知怎的,我在標線得到一個空引用異常。通過調試它,我可以確認lastString實際上是空的,儘管被包裹在一個空檢查中,並且lastString永遠不會被設置爲null。

這只是在複雜的流動情況爲好,這讓我想到垃圾回收是某種考慮我的實際WeakReference的對象,而不僅僅是它的目標。

有人可以告訴我以這是怎麼發生的,什麼是最好的行動當然是?

編輯: 我不能在這一切的原因確定。我結束了在try-catch中包裝錯誤代碼,現在就解決它。我對這個問題的根本原因非常感興趣。我一直試圖在一個簡單的測試案例中重現這一點,但事實證明這很難做到。此外,這僅在單元測試運行器下運行時纔會發生。如果我將代碼調整到最低限度,運行TestDriven和Gallio時將會繼續崩潰,但在放入控制檯應用程序時不會失敗

+1

有這個envolved任何mutlthreading? – Tigran

+0

@Tigran我無法在獨立的簡單測試用例中重現這一點。它所在的程序是多線程的,但是這個特定的對象不應該一次被多個線程訪問(我可以用調試器合理確定地確認) – Earlz

+0

每次執行「複雜流程」時都會發生這種情況嗎?只是偶爾? – Cemafor

回答

1

這最終是一個很難找到邏輯錯誤那是顯而易見的。

違規的if語句真的更像是這樣的:

if(lastString!=null && limiter==null || limiter=lastLimiter) 

這樣做的真正的分組更像是這樣的:

if((lastString!=null && limiter==null) || limiter=lastLimiter) 

正如墨菲法則將決定,不知何故,在這一個無關的測試情況下,lastLimiterlastString得到設置爲null通過的方法中使用任何地方,但這個單個測試用例。

所以啊,在CLR沒有錯誤,只是我自己的邏輯錯誤,是很難發現