我期待有效地實現以下方法:Roslyn:枚舉確切的標記+瑣事跨越單一源代碼行?
IEnumerable<ColoredSpan> GetSyntaxHighlightedSpansOnLine(int lineNumber);
我有一個Document
,SourceText
,SyntaxTree
等。假設ColoredSpan
是一些顏色和字符串的元組(或其他來源char
s)。對於例如第三行這段代碼:
namespace Foo
{ /* Badly formatted coment...
which continues here... */ class Bar : public IBaz // TODO: rename classes
{
...
我期待與文本交付枚舉的結果:
" ", "which continues here... */", " ", "class", " ", "Bar", " ",
":", " ", "public", " ", "IBaz", " ", "// TODO: rename classes", "\r\n"
注意包含空格和評論瑣事,和部分多評論。
Another answer指向派生CSharpSyntaxWalker來遍歷AST的整個部分,但不能有效地限制遍歷單行節點的方法。在每行的基礎上,這是不高效的,我不能輕易地確定例如Roslyn「trivia」(例如多行註釋)返回。它也返回重疊的節點(例如命名空間)。
我試圖code as in this answer,一拉:
var lineSpan = sf.GetText().Lines[lineNumber].Span;
var nodes = syntaxTree.GetRoot()
.DescendantNodes()
.Where(x => x.Span.IntersectsWith(lineSpan))
但這返回整個子樹AST,前序遍歷,而這又是低效的,並且還返回重疊節點(例如命名空間),並且不處理瑣事。其他樣本適用於整個文檔/腳本。我還諮詢了接近零的API文檔。
代碼分析API是否有效地允許這樣做?或者爲了實現這個方法,我是否需要提前遍歷整個AST,並存儲一個我自己設計的主觀龐大並行內存消耗的數據結構,如this answer?
不完全確定我們應該在這裏添加哪些文檔該代碼與我們在Visual Studio中使用的代碼相同,但是有一些緩存是我們在其上面的。緩存問題很棘手,說實話,如果不知道該場景,很難回答。 –
@JasonMalinowski這是超級安慰,謝謝 - 至少在這裏的正確線條。雖然我們可以看到Roslyn代碼非常棒,但評論很少,所以很難從實現中推導出API合約,所以很難知道其中的API是按照預期編寫的,而不是濫用API /吠叫錯誤的樹/爲未來的自我創造糟糕的表現問題。順便提一下,在Roslyn概述wiki中看到提及語法突出顯示和分類器會很高興。但我真的應該在Github上提出這樣的建議。 –