Jump to content

What is faster?


IIYAMA

Recommended Posts

  • Moderators

What is a faster way to use? (I need to check a lot all the players.)

  
getElementsByType("player") 
  
--or 
  
-- a table that already contains all players? 
local myPlayers = {} 
  
  
  
  
for I, player in ipairs () do 
  
end 
  

Link to comment

I think the first would be the fastest. If you do it the second way, you have to keep updating the table.

Also, if you want to check lots of players, I would recommend just getting a list of players eligible for the thing you want (if applicable).

Link to comment
  • Moderators

Well updating the table isn't the problem, I am talking about looping through a table that is active every 0.3 seconds. (only when the timer should be active)

When I use getElementsByType("player") it will update the whole table again and after executing the data will be gone.

But when I update this table with onPlayerJoin and onPlayerQuit. I don't have to reload the whole table, but it will remain in to the memory.

Link to comment
  • Moderators

Sample:

local myPlayers = {} 
  
addEventHandler ( "onPlayerQuit", getRootElement(),  
function () 
  for i, player in ipairs(myPlayers) do 
    if player == source then 
      table.remove (myPlayers,i) 
      return 
    end 
  end 
end) 
  
addEventHandler ( "onPlayerJoin", getRootElement(),  
function () 
  table.insert (myPlayers,source) 
end) 
  
setTimer (function () 
for i, player in ipairs(myPlayers) do 
  
end,300,1) 
  
 -- or ------------------------------------------- 
  
setTimer (function () 
  for i, player in ipairs(getElementsByType ("player")) do 
  end 
end,300,1) 
  

Edited by Guest
Link to comment

Updating the table is faster than using getElementsByType every time. When you call getElementsByType, you are creating a new table and doing this every 0.3 seconds isn't efficient. When you update the table, the slowest code to execute is looping through all players and using table.remove (which also pushes all elements back by one index) and doing this when the player leaves isn't that much. So if you're after performance, update the table instead of creating a new one. By the way, it's better to use the player element as the key for the table:

--onPlayerJoin 
myPlayers[source] = true 
  
--onPlayerQuit 
myPlayers[source] = nil 
  
--looping through all players: 
for player in pairs(myPlayers) do 
  
end 

No need to loop through the table on quit, Lua will take care of what's needed, resulting in best performance.

Link to comment
Can you loop key's O_o?

What do you mean?

There are 2 functions for iteration.

pairs and ipairs

http://www.lua.org/pil/7.3.html

Also, I've mentioned that in someone's topic that getElementsByType is not recommended for very frequent use for server. You can use client's power for this since most servers don't have as much processing power as client's PC. For you it will be more efficient to use a global table and update it when needed.

Link to comment
  • Moderators
pairs and ipairs 

This was very unclear for me, I saw differed topic's about it, but they all gave differed answers and nobody seems to know the exact differences. Very confusing...

Ok, I will put them in a table

thank you all

Link to comment

ipairs can only iterate indexed tables that have the indexes in order (1,2,3,4,5,6,7,8,9 and so on) while pairs can iterate any kind of table. Instead of using these functions, you can use next, which will work for both indexed and non-indexed tables. Here's an example of its usage:

local table = { ["wheels"] = true, ["doors"] = true } 
local table2 = { [1] = "Hi, I'm ixjf!", [2] = "Bye!" } 
  
for k,v in next, table do 
    print ( k, v ); 
    --[[OUTPUT: 
        wheels  true 
        doors  true]] 
end 
  
for i,v in next, table2 do 
    print ( i, v ); 
    --[[OUTPUT: 
        1  Hi, I'm ixjf! 
        2  Bye!99]] 
end 

Edited by Guest
Link to comment
  • Moderators

hmm interesting

If I set a player to true. Let we say I got everyday 100 players in my server, will this table get any bigger? and will it gives more lagg at while using this for a long time before I reset the table: myTable ={}

  
myTable ={} 
myTable[player] = {} 
  
myTable[player] = nil 
  

Link to comment

The table will continuously get bigger, since you only set fields' value to nil, you don't actually remove them (you can however use table.remove to do that). I can't tell much about lag, but I'd say yes it would (principally when iterating, it will loop through all fields), though I don't think that would affect much the gameplay, if at all.

Link to comment
The table will continuously get bigger, since you only set fields' value to nil, you don't actually remove them (you can however use table.remove to do that). I can't tell much about lag, but I'd say yes it would (principally when iterating, it will loop through all fields), though I don't think that would affect much the gameplay, if at all.

That's wrong, when speaking about performance. Calling the function is definitely slower and setting it to nil will suffice in most cases, even if the table isn't rehashed in lua.

Link to comment

When you set the value of the field to nil, that field is removed, so the memory will be freed. That's the point of nil - it is a way to represent the absence of the value. That's the reason why you get nil from non-existing variables or uninitialized fields of the table. If nil didn't have such special behavior, it would be not different from false, therefore an useless duplicate.

Link to comment
When you set the value of the field to nil, that field is removed, so the memory will be freed. That's the point of nil - it is a way to represent the absence of the value. That's the reason why you get nil from non-existing variables or uninitialized fields of the table. If nil didn't have such special behavior, it would be not different from false, therefore an useless duplicate.

Yes, it's true for most languages, but not for Lua. Setting a single value as nil doesn't force a rehash, so the table size remains the same (initially). Though as I mentioned, that is not a problem in most cases anyways.

Link to comment
  • Moderators

Well guys,

http://lua-users.org/wiki/StoringNilsInTables

Storing Nils In Tables

Lua tables make no distinction between a table value being nil and the corresponding key not existing in the table. t = {[k] = nil} is identical to t = {} , and t[k] evaluates to nil when k is not a table key. In fact, you may think of {} as a table with all possible keys set to nil, and this still takes only a small finite amount of memory because all those keys having nil values are not explicitly stored. Furthermore, attempting to set a table key as nil, e.g. {[nil] = true} , raises a run-time error. This is unlike various other common languages. [1]

I do it my way. :D

local lossObjectT = 0 
function objectTimer () 
    for k, objectTable in pairs (objectExpl) do 
        local Timer = objectTable[2] 
        if Timer then 
            Timer = Timer - 1 
            if Timer > 0 then 
                objectExpl[k][2] = Timer 
            else 
                objectExpl[k][2] = nil 
                local object = objectTable[1] 
                if isElement(object) then 
                    activateObject(object,objectTable[3])        
                end 
            end 
        end 
    end 
    lossObjectT = lossObjectT +1 
    if lossObjectT > 5 then 
        lossObjectT = 0 
        for i, objectTable in pairs (objectExpl) do 
            while objectExpl[ i ] and not objectExpl[ i ][2] do 
                table.remove(objectExpl,i) 
            end 
        end 
    end 
    if #objectExpl <= 0 and isTimer(objectExplTimer) then 
        killTimer(objectExplTimer) 
    end 
end 

I may can set the table like this: objectExpl = {}

when I stop the timer, but I am not sure if that is better then remove with table.remove.

I have seriously no idea how you guy would script this.

Link to comment
When you set the value of the field to nil, that field is removed, so the memory will be freed. That's the point of nil - it is a way to represent the absence of the value. That's the reason why you get nil from non-existing variables or uninitialized fields of the table. If nil didn't have such special behavior, it would be not different from false, therefore an useless duplicate.

Yes, it's true for most languages, but not for Lua. Setting a single value as nil doesn't force a rehash, so the table size remains the same (initially). Though as I mentioned, that is not a problem in most cases anyways.

Garbage collector will deal with it. Setting value of nil will "remove" the field from a table as well as memory. This is also what you have to do when clearing shader/texture from memory. Simple destroyElement will only destroy the MTA element from memory but the memory address (a value) in a variable is still there, therefore it is necessary to nil the variable in order to free the RAM.

Simple example explaining nil'ing variables:

local tab = { 1,2,3,4,5,6 }; -- simple indexed table of size: 6 
  
function table.size( t ) 
    local i = 0; 
    for k,v in pairs( t ) -- I use pairs in case "t" will be non-indexed table or one of table fields will be nil 
        i = i + 1; 
    end 
    return i; 
end 
  
print( table.size( tab ) ); -- this will show you 6 
tab[ 2 ] = false; -- assign new value of false to index 2 
print( table.size( tab ) ); -- it's still 6 
tab[ 2 ] = nil; -- delete the field at index 2 
print( table.size( tab ) ); -- now you will see 5 because tab[2] does not hold any value and therefore size of the table will change 
  

Link to comment

Just a question:

You have at least 1 GB RAM, at least 2 GHz of CPU...

What does it matter if the table is 1 KB bigger?

About pairs and ipairs:

in a benchmark, pairs is faster than ipairs, but ipairs is sorted for sure.

Also, have you ever benchmarked "getElementsByType" and the table yourself? Just let it run 200 times and check how long it takes. I'd still use "getElementsByType" since it is easier to manage and less prone to bugs. Also don't forget that calling a code each 300 ms is kind of useless. It just means that the LUA engine has more stuff to do, even though it doesn't need to do it.

Link to comment

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...