diff options
author | 最萌小汐 <sumneko@hotmail.com> | 2020-11-03 10:30:01 +0800 |
---|---|---|
committer | 最萌小汐 <sumneko@hotmail.com> | 2020-11-03 10:30:01 +0800 |
commit | 0237e54f0ac5a4a4ee94c1f5bebdf69e88e46c7e (patch) | |
tree | 563a3d08999f2a699bb02c039e9ce215da500987 /script-beta | |
parent | 57cea535eecca00f208e39f9afbbaab68f152c05 (diff) | |
download | lua-language-server-0237e54f0ac5a4a4ee94c1f5bebdf69e88e46c7e.zip |
将文件的 ast 与 lines 信息缓存在弱表里,使内存占用降低了75%,但是诊断耗时增加了50%
Diffstat (limited to 'script-beta')
-rw-r--r-- | script-beta/files.lua | 118 |
1 files changed, 64 insertions, 54 deletions
diff --git a/script-beta/files.lua b/script-beta/files.lua index ead75079..6f4d1ce9 100644 --- a/script-beta/files.lua +++ b/script-beta/files.lua @@ -18,6 +18,8 @@ m.notifyCache = {} m.assocVersion = -1 m.assocMatcher = nil m.globalVersion = 0 +m.linesMap = setmetatable({}, { __mode = 'v' }) +m.astMap = setmetatable({}, { __mode = 'v' }) --- 打开文件 ---@param uri string @@ -113,8 +115,8 @@ function m.setText(uri, text) return end file.text = text - file.ast = nil - file.lines = nil + m.linesMap[uri] = nil + m.astMap[uri] = nil file.cache = {} file.cacheActiveTime = math.huge file.version = file.version + 1 @@ -172,7 +174,9 @@ function m.removeAll() m.globalVersion = m.globalVersion + 1 await.close('files.version') for uri in pairs(m.fileMap) do - m.fileMap[uri] = nil + m.fileMap[uri] = nil + m.astMap[uri] = nil + m.linesMap[uri] = nil m.onWatch('remove', uri) end --m.notifyCache = {} @@ -183,21 +187,8 @@ function m.eachFile() return pairs(m.fileMap) end ---- 获取文件语法树 ----@param uri string ----@return table ast -function m.getAst(uri) - if platform.OS == 'Windows' then - uri = uri:lower() - end - if uri ~= '' and not m.isLua(uri) then - return nil - end - local file = m.fileMap[uri] - if not file then - return nil - end - if #file.text >= config.config.workspace.preloadFileSize * 1000 then +function m.compileAst(uri, text) + if #text >= config.config.workspace.preloadFileSize * 1000 then if not m.notifyCache['preloadFileSize'] then m.notifyCache['preloadFileSize'] = {} m.notifyCache['skipLargeFileCount'] = 0 @@ -210,44 +201,61 @@ function m.getAst(uri) proto.notify('window/showMessage', { type = 3, message = lang.script('WORKSPACE_SKIP_LARGE_FILE' - , ws.getRelativePath(file.uri) + , ws.getRelativePath(uri) , config.config.workspace.preloadFileSize - , #file.text / 1000 + , #text / 1000 ), }) end end - file.ast = nil return nil end - if file.ast == nil then - local clock = os.clock() - local state, err = parser:compile(file.text - , 'lua' - , config.config.runtime.version - , { - special = config.config.runtime.special, - } - ) - local passed = os.clock() - clock - if passed > 0.1 then - log.warn(('Compile [%s] takes [%.3f] sec, size [%.3f] kb.'):format(uri, passed, #file.text / 1000)) - end - if state then - state.uri = file.uri - state.ast.uri = file.uri - file.ast = state - if config.config.luadoc.enable then - parser:luadoc(state) - end - else - log.error(err) - file.ast = false - return nil + local clock = os.clock() + local state, err = parser:compile(text + , 'lua' + , config.config.runtime.version + , { + special = config.config.runtime.special, + } + ) + local passed = os.clock() - clock + if passed > 0.1 then + log.warn(('Compile [%s] takes [%.3f] sec, size [%.3f] kb.'):format(uri, passed, #text / 1000)) + end + if state then + state.uri = uri + state.ast.uri = uri + if config.config.luadoc.enable then + parser:luadoc(state) end + return state + else + log.error(err) + return nil + end +end + +--- 获取文件语法树 +---@param uri string +---@return table ast +function m.getAst(uri) + if platform.OS == 'Windows' then + uri = uri:lower() + end + if uri ~= '' and not m.isLua(uri) then + return nil + end + local file = m.fileMap[uri] + if not file then + return nil + end + local ast = m.astMap[uri] + if not ast then + ast = m.compileAst(uri, file.text) + m.astMap[uri] = ast end file.cacheActiveTime = timer.clock() - return file.ast + return ast end --- 获取文件行信息 @@ -261,10 +269,12 @@ function m.getLines(uri) if not file then return nil end - if not file.lines then - file.lines = parser:lines(file.text) + local lines = m.linesMap[uri] + if not lines then + lines = parser:lines(file.text) + m.linesMap[uri] = lines end - return file.lines + return lines end --- 获取原始uri @@ -355,10 +365,10 @@ function m.onWatch(ev, ...) end function m.flushCache() - for _, file in pairs(m.fileMap) do + for uri, file in pairs(m.fileMap) do file.cacheActiveTime = math.huge - file.ast = nil - file.lines = nil + m.linesMap[uri] = nil + m.astMap[uri] = nil file.cache = {} end end @@ -372,8 +382,8 @@ function m.flushFileCache(uri) return end file.cacheActiveTime = math.huge - file.ast = nil - file.lines = nil + m.linesMap[uri] = nil + m.astMap[uri] = nil file.cache = {} end |