first queries impl

This commit is contained in:
BlackMATov
2024-11-14 02:57:56 +07:00
parent d2112b3a40
commit b421b1704f
4 changed files with 312 additions and 158 deletions

View File

@@ -17,4 +17,12 @@ do
local query = registry:query(
fragments.position,
fragments.velocity)
for chunk in query:chunks() do
local ps = chunk.components[fragments.position]
local vs = chunk.components[fragments.position]
for i = 1, #chunk.entities do
end
end
end

78
develop/iterators.lua Normal file
View File

@@ -0,0 +1,78 @@
local iterators = {}
---@generic K
---@param t table<K, any>
---@return fun(): K
function iterators.keys(t)
if #t > 0 then
local i = 0
return function()
i = i + 1
if i <= #t then
return i
end
end
else
local k = nil
return function()
local v
k, v = next(t, k)
if k ~= nil then
return k
end
end
end
end
---@generic V
---@param t table<any, V>
---@return fun(): V?
function iterators.values(t)
if #t > 0 then
local i = 0
return function()
i = i + 1
if i <= #t then
return t[i]
end
end
else
local k = nil
return function()
local v
k, v = next(t, k)
if k ~= nil then
return v
end
end
end
end
---@generic V
---@param iter fun(): V?
---@return integer
function iterators.count(iter)
local count = 0
for _ in iter do count = count + 1 end
return count
end
---@generic V
---@param iter fun(): V?
---@param func fun(v: V): boolean
---@return fun(): V?
function iterators.filter(iter, func)
return function()
while true do
local v = iter()
if v == nil then
return
end
if func(v) then
return v
end
end
end
end
return iterators

View File

@@ -1,4 +1,6 @@
local evolved = require 'evolved'
local iterators = require 'develop.iterators'
local utilities = require 'develop.utilities'
---@param name string
@@ -25,36 +27,8 @@ local function describe(name, func, ...)
collectgarbage('restart')
end
describe('random entity:insert', function()
for _ = 1, 1000 do
local registry = evolved.registry()
---@type evolved.entity[]
local all_fragments = {}
local all_fragment_count = math.random(1, 10)
for i = 1, all_fragment_count do all_fragments[i] = registry:entity() end
for _ = 1, 100 do
local e1, e2 = registry:entity(), registry:entity()
---@type evolved.entity[]
local insert_fragments = {}
local insert_fragment_count = math.random(1, 10)
for i = 1, insert_fragment_count do insert_fragments[i] = all_fragments[math.random(1, all_fragment_count)] end
utilities.shuffle_array(insert_fragments)
for _, fragment in ipairs(insert_fragments) do e1:insert(fragment) end
utilities.shuffle_array(insert_fragments)
for _, fragment in ipairs(insert_fragments) do e2:insert(fragment) end
assert(e1.chunk == e2.chunk)
end
end
end)
describe('random entity:remove', function()
for _ = 1, 1000 do
describe('entity:chunk', function()
for _ = 1, 500 do
local registry = evolved.registry()
---@type evolved.entity[]
@@ -93,3 +67,61 @@ describe('random entity:remove', function()
end
end
end)
describe('query:chunks', function()
for _ = 1, 500 do
local registry = evolved.registry()
---@type evolved.entity[]
local all_fragments = {}
local all_fragment_count = math.random(1, 10)
for i = 1, all_fragment_count do all_fragments[i] = registry:entity() end
local function check_all_queries()
for _, q in ipairs(registry.queries) do
local query_chunk_count = iterators.count(q:chunks())
local registry_chunk_count = iterators.count(iterators.filter(
iterators.values(registry.chunks),
function(chunk) return chunk:has_all_fragments(unpack(q.fragments)) end))
assert(query_chunk_count == registry_chunk_count)
end
end
---@param n integer
local function create_queries(n)
for _ = 1, n do
---@type evolved.entity[]
local query_fragments = {}
local query_fragment_count = math.random(1, 5)
for i = 1, query_fragment_count do
query_fragments[i] = all_fragments[math.random(1, all_fragment_count)]
end
registry:query(unpack(query_fragments))
end
end
---@param n integer
local function create_entities(n)
for _ = 1, n do
---@type evolved.entity[]
local insert_fragments = {}
local insert_fragment_count = math.random(1, 10)
for i = 1, insert_fragment_count do
insert_fragments[i] = all_fragments[math.random(1, all_fragment_count)]
end
local e = registry:entity()
for _, fragment in ipairs(insert_fragments) do e:insert(fragment) end
end
end
create_entities(50)
create_queries(10)
check_all_queries()
create_entities(50)
create_queries(10)
check_all_queries()
end
end)