[code]print("pairs")
start = SysTime()
for k, v in pairs(_G) do
// do nothing
end
print(SysTime() - start)
print("weird loop?")
start = SysTime()
for i = 1, #_G do
// do nothing
end
print(SysTime() - start)
print("next")
start = SysTime()
for k, v in next, _G do
// do nothing
end
print(SysTime() - start)
local i = 0
print("repeat/until")
start = SysTime()
repeat
i = i + 1
until i >= table.Count(_G)
print(SysTime() - start)[/code]
[img]http://4st.me/YXoHX.png[/img]
Which is fastest?
My math is terrible, by the way.
EDIT: There's an error in this code, continue reading to further see the results.
You are mixing #_G and table.Count(_G)
Stick to one for controlled results.
pairs = 0.000026895580958808
weird loop = 0.00000025614826881792
next = 0.000022284910301096
weird loop wins
repeat (using #_G instead of table.Count) comes out to 0.0000011702754818543
[QUOTE=AnonTakesOver;47455170]You are mixing #_G and table.Count(_G)
Stick to one for controlled results.[/QUOTE]
No wonder, I was wondering why Repeat was so slow, thanks for telling me I was being a dumbfuq.
[img]http://4st.me/64DlQ.png[/img]
Huh...results are better but I'm still unsure, while, weird loop, and repeat all return the same thing, I'm guessing one number is different somewhere but it's unable to output it because of decimals.
[QUOTE=yea;47455172]pairs = 0.000026895580958808
weird loop = 0.00000025614826881792
next = 0.000022284910301096
weird loop wins
repeat (using #_G instead of table.Count) comes out to 0.0000011702754818543[/QUOTE]
its faster because its not doing anything -- _G isnt an array, so #_G == 0 and the loop is never even executed.
your repeat loop wont do anything useful either, since _G doesnt have integer keys, but it seems so slow because your loop executes for each item in _G and calls table.Count each time it executes, which [i]also[/i] iterates over every item in _G. never ever do that.
`pairs(tbl)` returns `next, tbl`,
so `next, tbl` is the same as `pairs(tbl)` just without extra function call,
so there's no reason to use `pairs(tbl)` over `next, tbl`.
(Be a bit cautious when using some function's result as table for iteration, you need to surround function call in braces if function returns several values (file.Find, for example).)
[QUOTE=vigi8;47455227]`pairs(tbl)` returns `next, tbl`
so `next, tbl` is the same as `pairs(tbl)` just without extra function call
so there's no reason to use `pairs(tbl)` over `next, tbl`[/QUOTE]
Who's idea was it to even make pairs then? On-topic
[img]http://4st.me/BALZS.png[/img]
It looks like next is the fastest, every now and then it ends up being the same speed as the weird loop, and it looks like while and repeat are the slowest. I don't understand why sometimes weird loop goes super fast, though, as pictured it sometimes goes down to even 0.000001 and next seems to stay at 0.000003
[QUOTE=vigi8;47455227]`pairs(tbl)` returns `next, tbl`,
so `next, tbl` is the same as `pairs(tbl)` just without extra function call,
so there's no reason to use `pairs(tbl)` over `next, tbl`.
(Be a bit cautious when using some function's result as table for iteration, you need to surround function call in braces if function returns several values (file.Find, for example).)[/QUOTE]
readability is generally better than micro-optimization unless you're planning to call this hypothetical function a few dozen times in HUDPaint -- i mean youre talking about a 4 microsecond performance increase
[QUOTE=Luni;47455222]its faster because its not doing anything -- _G isnt an array, so #_G == 0 and the loop is never even executed.
your repeat loop wont do anything either, since _G doesnt have integer keys, but table.Count is iterating over it every single time the loop executes -- which executes for every item in _G -- which is why it seems so slow. never ever do that.[/QUOTE]
you're right, gave the loop something to do (more or less)
looped through players in a local mp game (7 bots + the player, all bots dead)
[code]
print("pairs")
start = SysTime()
for k, v in pairs(player.GetAll()) do
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("weird loop?")
start = SysTime()
for i = 1, #player.GetAll() do
v = player.GetAll()[i]
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("next")
start = SysTime()
for k, v in next, player.GetAll() do
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("repeat/until")
start = SysTime()
i = 0
repeat
i = i + 1
p = player.GetAll()[i]
if p:Alive() then
// do nothing
end
until i >= #player.GetAll()
print(SysTime() - start)
print("while")
start = SysTime()
i = 0
while (i < #player.GetAll()) do
i = i + 1
v = player.GetAll()[i]
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
[/code]
[code]
pairs
1.1410187653382e-005 (0.000011410187653382)
weird loop?
1.8431842363498e-005 (0.000018431842363498)
next
3.8033958844608e-006 (0.0000038033958844608)
repeat/until
2.9549461942224e-005 (0.000029549461942224)
while
5.1492131206032e-005 (0.000051492131206032)
[/code]
looks like next wins
[QUOTE=Luni;47455247]readability is generally better than micro-optimization unless you're planning to call this hypothetical function a few dozen times in HUDPaint -- i mean youre talking about a 4 microsecond performance increase[/QUOTE]
[code]for k, v in pairs(player.GetAll()) do -- #1[/code]
[code]for k, v in next, player.GetAll() do -- #2[/code]
[code]for k, v in pairs(file.Find("*", "DATA")) do -- #3[/code]
[code]for k, v in next, (file.Find("*", "DATA")) do -- #4[/code]
#2 seems more readable to me than #1, no extra braces.
#3 and #4 are kinda the same, and such functions are minority anyway.
[QUOTE=yea;47455262]you're right, gave the loop something to do (more or less)
looped through players in a local mp game (7 bots + the player, all bots dead)
[code]
print("pairs")
start = SysTime()
for k, v in pairs(player.GetAll()) do
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("weird loop?")
start = SysTime()
for i = 1, #player.GetAll() do
v = player.GetAll()[i]
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("next")
start = SysTime()
for k, v in next, player.GetAll() do
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
print("repeat/until")
start = SysTime()
i = 0
repeat
i = i + 1
p = player.GetAll()[i]
if p:Alive() then
// do nothing
end
until i >= #player.GetAll()
print(SysTime() - start)
print("while")
start = SysTime()
i = 0
while (i < #player.GetAll()) do
i = i + 1
v = player.GetAll()[i]
if v:Alive() then
// do nothing
end
end
print(SysTime() - start)
[/code]
[code]
pairs
1.1410187653382e-005 (0.000011410187653382)
weird loop?
1.8431842363498e-005 (0.000018431842363498)
next
3.8033958844608e-006 (0.0000038033958844608)
repeat/until
2.9549461942224e-005 (0.000029549461942224)
while
5.1492131206032e-005 (0.000051492131206032)
[/code]
looks like next wins[/QUOTE]
your code is broken for the weird loop
you have to call player.GetAll() only once, since that's what all the other ones do
same with while loop
[QUOTE=MeepDarknessM;47456573]your code is broken for the weird loop
you have to call player.GetAll() only once, since that's what all the other ones do
same with while loop[/QUOTE]
Yeah, his code was wrong, I showed him mine though (he's a friend of mine) and we determined that next is still the fastest, my code only called player.GetAll() once. I don't know why he made that mistake, but it was absolutely fine in my code, I don't have it to post anymore since I deleted it after I finished working with loops.
TL;DR Next is still faster from what I've seen.
LuaJIT handles for loops in a specialized way, while it just uses conditional jumps to handle while and repeat loops. I would assume numeric for loops are faster, but evidently it also optimizes pairs. As other's have pointed out, all the numeric stuff isn't going to work on stuff with string keys, so your best option is probably to use the iterator version.
There are all sorts of goofy optimization quirks in lua. For instance, local variables are generally way faster than global ones, and the # operator is almost certainly way faster than table.Count. Not that it probably matters. As some dude called Donald Knuth said, "Premature optimization is the root of all evil".
EDIT: Oh! [URL="http://wiki.luajit.org/Bytecode-2.0"]Source[/URL]
Sorry, you need to Log In to post a reply to this thread.