![](/img/trans.png)
[英]How can i find what cause a null exception ? I mean what line or where in the code the exception throw?
[英]How can we easily find what line in the code causes a runtime exception?
考慮以下分析器:
public void AnalyzeNode(SyntaxNode node, SemanticModel semanticModel, Action<Diagnostic> addDiagnostic, CancellationToken cancellationToken)
{
var throwStatement = node as ThrowStatementSyntax;
var isObjectCreationExpression = throwStatement.Expression is ObjectCreationExpressionSyntax;
var obj = throwStatement.Expression as ObjectCreationExpressionSyntax;
var isCorrectTypeOfExpression = (obj.Type as IdentifierNameSyntax).Identifier.Text == typeof(ArgumentException).Name;
}
使用SyntaxKind.ThrowStatement
作為興趣點。
如果拋出的異常沒有在new Exception()
聲明,那么obj
應該為null
,而是表示為throw e
,其中e
是先前聲明的異常。
當在之后調用obj.Type
時,這反過來將拋出NullReferenceException
。
有問題的例子:
static void Method1()
{
throw new ArgumentException();
}
static void Method2(ArgumentException e)
{
throw e;
}
第一次throw
會很好地通過分析器,但第二次throw
會導致obj
為null
因為它不是ObjectCreationExpressionSyntax
類型。
在沙箱Visual Studio環境中,這將顯示為信息消息:
用戶診斷分析器'FormattingFixes.EmptyArgumentException.ArgumentExceptionAnalyzer'拋出異常,並顯示消息'對象引用未設置為對象的實例。'。
在這個簡短的樣本中,很容易分辨問題所在,但在一個不那么人為的例子中,它將更難發現。 行和列都是1
,沒有幫助。
在“傳統”編程中,您的環境會自動顯示拋出運行時異常的位置以及該時間點的值。 我可以在我的代碼中的某個地方放置一個隨機斷點,每次命中時查看所有值,並嘗試從那里推斷出它,但是一旦節點數遠遠高於這些值,這就不能很好地擴展。
我們如何輕松找到代碼中的哪一行導致運行時異常?
所以你應該還是休息一下,但如果你沒有要檢查的東西:
轉到“調試”菜單下,然后選擇“例外”。 您將看到“Thrown”或“User-unhandled”列。 使用Find查找NullReferenceException,並選中“thrown”復選框。 一旦拋出NullReferenceException,這將導致VS中斷。 如果你想要非常積極,你可以告訴它打破所有例外。
如果仍然無效,請轉到工具>選項,調試,常規並清除“僅我的代碼”。 這里需要注意的是,這會破壞所有例外情況,包括VS部分甚至不是你的錯。 (可悲的是,我們在很多不同的地方都拋出了很多例外。)
如果您願意,請隨意提交錯誤,以便我們可以將消息包括堆棧跟蹤和行/列,以便更容易調試。
因為我在這里:你的代碼確實如此
var isCorrectTypeOfExpression = (obj.Type as IdentifierNameSyntax).Identifier.Text == typeof(ArgumentException).Name;
注意語法檢查 - 如果我寫了throw new System.ArgumentException()
會發生什么? 正確的方法是獲取語義模型並綁定ObjectCreationExpression以確定實際類型是什么。 (如果你在意的話,這也意味着你在別名的情況下工作。)
使用以下步驟獲取引發異常的行號。
以下是代碼段。
try
{
//TODO
throw new Exception();
}
catch (Exception ex)
{
var stacktrace = new StackTrace(ex, true);
var frame = st.GetFrame(0);
var filelinenumber = frame.GetFileLineNumber();
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.