aboutsummaryrefslogtreecommitdiff
path: root/runtime/lua/vim/iter.lua
diff options
context:
space:
mode:
Diffstat (limited to 'runtime/lua/vim/iter.lua')
-rw-r--r--runtime/lua/vim/iter.lua34
1 files changed, 25 insertions, 9 deletions
diff --git a/runtime/lua/vim/iter.lua b/runtime/lua/vim/iter.lua
index 56012e9b9f..0e98d0437e 100644
--- a/runtime/lua/vim/iter.lua
+++ b/runtime/lua/vim/iter.lua
@@ -66,7 +66,7 @@ end
---@class ListIter : Iter
---@field _table table Underlying table data
---@field _head number Index to the front of a table iterator
----@field _tail number Index to the end of a table iterator
+---@field _tail number Index to the end of a table iterator (exclusive)
local ListIter = {}
ListIter.__index = setmetatable(ListIter, Iter)
ListIter.__call = function(self)
@@ -321,17 +321,33 @@ end
---@private
function ListIter.totable(self)
- if self._head == 1 and self._tail == #self._table + 1 and self.next == ListIter.next then
- -- Sanitize packed table values
- if getmetatable(self._table[1]) == packedmt then
- for i = 1, #self._table do
- self._table[i] = sanitize(self._table[i])
- end
+ if self.next ~= ListIter.next or self._head >= self._tail then
+ return Iter.totable(self)
+ end
+
+ local needs_sanitize = getmetatable(self._table[1]) == packedmt
+
+ -- Reindex and sanitize.
+ local len = self._tail - self._head
+
+ if needs_sanitize then
+ for i = 1, len do
+ self._table[i] = sanitize(self._table[self._head - 1 + i])
+ end
+ else
+ for i = 1, len do
+ self._table[i] = self._table[self._head - 1 + i]
end
- return self._table
end
- return Iter.totable(self)
+ for i = len + 1, table.maxn(self._table) do
+ self._table[i] = nil
+ end
+
+ self._head = 1
+ self._tail = len + 1
+
+ return self._table
end
--- Fold an iterator or table into a single value.