Visual studio code VSCode语言扩展,具有分层大纲、DocumentSymbol
我正在尝试使用VScode中的自定义语言来获取大纲。我有下面的代码,但我觉得它是缓慢的,因为我在课堂上找到一个范围的方式。是否有更好的方法找到范围并分配子项。我考虑过只跟踪括号的深度,并将更高深度的所有函数/方法/类分配到上一个深度的最后一项中 它是根据一本书改编的 类JSLDocumentSymbolProvider实现vscode.DocumentSymbolProvider{ 公共提供的文档符号(文档:vscode.TextDocument, 令牌:vscode.CancellationToken):表{ 返回新承诺((解决、拒绝)=>{ 变量符号:vscode.DocumentSymbol[]=[]; var深度=0; 对于(var i=0;iVisual studio code VSCode语言扩展,具有分层大纲、DocumentSymbol,visual-studio-code,vscode-extensions,Visual Studio Code,Vscode Extensions,我正在尝试使用VScode中的自定义语言来获取大纲。我有下面的代码,但我觉得它是缓慢的,因为我在课堂上找到一个范围的方式。是否有更好的方法找到范围并分配子项。我考虑过只跟踪括号的深度,并将更高深度的所有函数/方法/类分配到上一个深度的最后一项中 它是根据一本书改编的 类JSLDocumentSymbolProvider实现vscode.DocumentSymbolProvider{ 公共提供的文档符号(文档:vscode.TextDocument, 令牌:vscode.CancellationT
}也许这是一个代码审查的问题,因为您声称代码有效且“速度很慢”?看起来您有很多嵌套循环;随着输入大小的增加,这些循环可能会导致严重的性能问题。请纠正我的错误,最坏情况下的时间复杂度是否为
O(n^3)
?@Peter,如果放在更好的地方,我可以移动它。我不知道有代码检查堆栈交换。不,一个函数可以创建一个类,该类可以包含包含函数的方法。这肯定不是最佳做法,但我以前见过。“不,一个函数可以创建一个类,该类可以包含包含函数的方法。这肯定不是最佳实践,但我以前见过。“我不知道你在说什么;我只是根据嵌套循环猜测你的代码的时间复杂度。也许这是一个需要代码审查的问题,因为你声称代码可以工作并且“速度很慢”?看起来您有很多嵌套循环;随着输入大小的增长,这些循环可能会导致严重的性能问题。如果我错了,请纠正我,最糟糕的时间复杂度是O(n^3)
?@Peter,如果放在更好的地方,我可以移动它。我不知道有代码检查堆栈交换。不,一个函数可以创建一个类,该类可以包含包含函数的方法。这肯定不是最佳做法,但我以前见过。“不,一个函数可以创建一个类,该类可以包含包含函数的方法。这肯定不是最佳实践,但我以前见过。”我不知道你在说什么;我只是根据嵌套循环猜测代码的时间复杂性。
class JSLDocumentSymbolProvider implements vscode.DocumentSymbolProvider {
public provideDocumentSymbols(document: vscode.TextDocument,
token: vscode.CancellationToken): Thenable<vscode.DocumentSymbol[]> {
return new Promise((resolve, reject) => {
var symbols: vscode.DocumentSymbol[] = [];
var depth = 0;
for (var i = 0; i < document.lineCount; i++) {
var line = document.lineAt(i);
var txt = line.text;
var ltxt = txt.toLowerCase();
let open_brackets = ltxt.match(/\(/g) || [];
let close_brackets = ltxt.match(/\)/g) || [];
// console.log(ltxt)
// console.log(open_brackets, close_brackets)
//console.log(i, open_brackets.length, close_brackets.length)
depth += open_brackets.length - close_brackets.length;
//console.log(depth);
if (ltxt.includes("define class(")) {
let sname = txt.trim().substr(14, txt.trim().length - 16); //this is hard coded right now but it's kind of working
let detail = "ARGS:x, y returns z";
let start_pos = new vscode.Position(i, 0);
let n_bracket = 1;
let i_char = 0;
//let children: vscode.DocumentSymbol[] = []
let ds = new vscode.DocumentSymbol(sname, detail, vscode.SymbolKind.Class, line.range, line.range);
for(var i_line = i; n_bracket > 0; i_line++){
let class_line = document.lineAt(i_line);
let mtxt = class_line.text;
let ic;
if(i == i_line) ic = 16;
else ic = 0;
for(i_char = ic; i_char < mtxt.length; i_char++){
if(mtxt[i_char] === "(") n_bracket++;
else if(mtxt[i_char] === ")") n_bracket--;
if(n_bracket === 0) break
}
if (/(\w[\w\d\s]*)=\s*method\({((?:\s*(?:\w[\w\d\s]*)(?:=[^,]*)?,?\s*)*)},/i.test(mtxt)) {
let result = mtxt.match(/(\w[\w\d\s]*)=\s*method\({((?:\s*(?:\w[\w\d\s]*)(?:=[^,]*)?,?\s*)*)},/i)!;
let mname = result[1].trim();
let m_details = ""
if(result.length == 3){
m_details = result[2].trim();
}
ds.children.push(new vscode.DocumentSymbol(mname, m_details, vscode.SymbolKind.Method, class_line.range, class_line.range));
}
if(n_bracket === 0) break
}
let end_pos = new vscode.Position(i_line, i_char);
let rng = new vscode.Range(start_pos, end_pos);
ds.range = rng;
//ds.children = children;
symbols.push(ds);
}
else if (/(\w[\w\d\s]*)=\s*function\({((?:\s*(?:\w[\w\d\s]*)(?:=[^,]*)?,?\s*)*)},/.test(ltxt)) {
let result = txt.match(/(\w[\w\d\s]*)=\s*function\({((?:\s*(?:\w[\w\d\s]*)(?:=[^,]*)?,?\s*)*)},/i)!;
let sname = result[1].trim();
let detail = "";
if(result.length == 3){
detail = "(" + result[2].trim() + ")";
}
symbols.push(new vscode.DocumentSymbol(sname, detail, vscode.SymbolKind.Function, line.range, line.range));
}
}
resolve(symbols);
});
}