diff options
author | NAKAI Tsuyoshi <82267684+uga-rosa@users.noreply.github.com> | 2023-04-14 19:01:08 +0900 |
---|---|---|
committer | GitHub <noreply@github.com> | 2023-04-14 12:01:08 +0200 |
commit | 7caf0eafd83b5a92f2ff219b3a64ffae4174b9af (patch) | |
tree | 5ef258ecfc37e9df9dc5951a2cccc4d30a8dc573 /runtime/lua/vim/shared.lua | |
parent | 33e90f513851c91325a016a1303c004a1388a170 (diff) | |
download | rneovim-7caf0eafd83b5a92f2ff219b3a64ffae4174b9af.tar.gz rneovim-7caf0eafd83b5a92f2ff219b3a64ffae4174b9af.tar.bz2 rneovim-7caf0eafd83b5a92f2ff219b3a64ffae4174b9af.zip |
feat(lua)!: add stricter vim.tbl_islist() and rename old one to vim.tbl_isarray() (#16440)
feat(lua)!: add stricter vim.tbl_islist(), rename vim.tbl_isarray()
Problem: `vim.tbl_islist` allows gaps in tables with integer keys
("arrays").
Solution: Rename `vim.tbl_islist` to `vim.tbl_isarray`, add new
`vim.tbl.islist` that checks for consecutive integer keys that start
from 1.
Diffstat (limited to 'runtime/lua/vim/shared.lua')
-rw-r--r-- | runtime/lua/vim/shared.lua | 47 |
1 files changed, 40 insertions, 7 deletions
diff --git a/runtime/lua/vim/shared.lua b/runtime/lua/vim/shared.lua index 7ecb56eb92..f700f4a6b3 100644 --- a/runtime/lua/vim/shared.lua +++ b/runtime/lua/vim/shared.lua @@ -320,10 +320,10 @@ function vim.tbl_isempty(t) return next(t) == nil end ---- We only merge empty tables or tables that are not a list +--- We only merge empty tables or tables that are not an array (indexed by integers) ---@private local function can_merge(v) - return type(v) == 'table' and (vim.tbl_isempty(v) or not vim.tbl_islist(v)) + return type(v) == 'table' and (vim.tbl_isempty(v) or not vim.tbl_isarray(v)) end local function tbl_extend(behavior, deep_extend, ...) @@ -554,15 +554,15 @@ function vim.spairs(t) end end ---- Tests if a Lua table can be treated as an array. +--- Tests if a Lua table can be treated as an array (a table indexed by integers). --- --- Empty table `{}` is assumed to be an array, unless it was created by --- |vim.empty_dict()| or returned as a dict-like |API| or Vimscript result, --- for example from |rpcrequest()| or |vim.fn|. --- ----@param t table Table ----@return boolean `true` if array-like table, else `false` -function vim.tbl_islist(t) +---@param t table +---@return boolean `true` if array-like table, else `false`. +function vim.tbl_isarray(t) if type(t) ~= 'table' then return false end @@ -570,7 +570,8 @@ function vim.tbl_islist(t) local count = 0 for k, _ in pairs(t) do - if type(k) == 'number' then + --- Check if the number k is an integer + if type(k) == 'number' and k == math.floor(k) then count = count + 1 else return false @@ -589,6 +590,38 @@ function vim.tbl_islist(t) end end +--- Tests if a Lua table can be treated as a list (a table indexed by consecutive integers starting from 1). +--- +--- Empty table `{}` is assumed to be an list, unless it was created by +--- |vim.empty_dict()| or returned as a dict-like |API| or Vimscript result, +--- for example from |rpcrequest()| or |vim.fn|. +--- +---@param t table +---@return boolean `true` if list-like table, else `false`. +function vim.tbl_islist(t) + if type(t) ~= 'table' then + return false + end + + local num_elem = vim.tbl_count(t) + + if num_elem == 0 then + -- TODO(bfredl): in the future, we will always be inside nvim + -- then this check can be deleted. + if vim._empty_dict_mt == nil then + return nil + end + return getmetatable(t) ~= vim._empty_dict_mt + else + for i = 1, num_elem do + if t[i] == nil then + return false + end + end + return true + end +end + --- Counts the number of non-nil values in table `t`. --- --- <pre>lua |