Optimizations
From GiderosMobile
Optimizations
When you're ready to optimize your game, this page can be helpful.
Distance
-- simple functions test timer by @antix
local random, sqrt = math.random, math.sqrt
local x1, y1 = random(-100000, 100000), random(-100000, 100000)
local x2, y2 = random(-100000, 100000), random(-100000, 100000)
local dx, dy
-- init test
local dist = math.distance(x1, y1, x2, y2)
print("*** POINT A: "..x1, y1, "POINT B: "..x2, y2)
print("*** DISTANCE: "..dist)
-- tests
local data = {
{
"sqrt",
function()
dx, dy = x2-x1, y2-y1
dist = sqrt(dx*dx + dy*dy)
end, -- 56ms
},
{
"exponent",
function()
dx, dy = x2-x1, y2-y1
dist = (dx^2 + dy^2)^0.5
end, -- 40ms
},
{
"multiply/exponent",
function()
dx, dy = x2-x1, y2-y1
dist = (dx*dx + dy*dy)^0.5
end, -- 43ms
},
{
"multiply/exponent without power",
function()
dx, dy = x2-x1, y2-y1
dist = dx*dx + dy*dy
end, -- 40ms but wrong result!
},
{
"math.distance",
function()
dist = math.distance(x1, y1, x2, y2)
end, -- 73ms
},
}
-- run all functions
for i = 1, #data do
local block = data[i]
local func = block[2]
local start = os.timer()
for i = 1, 1000000 do -- 1 million repetitions!
func()
end
local elapsed = math.floor((os.timer() - start) * 1000)
print(block[1].." ("..elapsed.."ms)", "", "", "", "", "distance: "..dist)
end
Sprite Sorting
-- sprite sorting (based on simple functions test timer by @antix)
local random = math.random
local sprites = {}
for i = 1, 64 do
sprites[i] = {}
sprites[i].spr1 = Pixel.new(0x0, 1, 64, 64)
sprites[i].spr1:setPosition(random(1, 640), 48) -- 48, 96
stage:addChild(sprites[i].spr1)
sprites[i].spr2 = Pixel.new(0xff0000, 1, 64, 64)
sprites[i].spr2:setPosition(random(1, 640), 64)
stage:addChild(sprites[i].spr2)
end
local spr1y, spr2y = 0, 0
-- tests
local data = {
{
"swap",
function()
for _, v in pairs(sprites) do
if v.spr1:getY() < v.spr2:getY() then
spr1y, spr2y = v.spr1:getY(), v.spr2:getY()
stage:swapChildren(v.spr1, v.spr2)
end
end
end, -- 816ms (much better than addChildAt)
},
{
"addChildAt",
function()
for _, v in pairs(sprites) do
if v.spr1:getY() < v.spr2:getY() then
spr1y, spr2y = v.spr1:getY(), v.spr2:getY()
stage:addChildAt(v.spr1, stage:getChildIndex(v.spr2))
end
end
end, -- 1272ms
},
{
"async swap",
function()
local function fun()
for _, v in pairs(sprites) do
if v.spr1:getY() < v.spr2:getY() then
spr1y, spr2y = v.spr1:getY(), v.spr2:getY()
stage:swapChildren(v.spr1, v.spr2)
end
end
end
Core.asyncCall(fun) -- profiler seems to be faster without asyncCall (because of pairs traversing?)
end, -- 29ms (the best but has some glitches!)
},
}
-- run all functions
for i = 1, #data do
local block = data[i]
local func = block[2]
local start = os.timer()
for i = 1, 25000 do func() end -- 12500
local elapsed = math.floor((os.timer() - start) * 1000)
print(block[1].." ("..elapsed.."ms)", spr1y, spr2y)
end
More to come, God's willing!