Wednesday, April 18, 2012

Why I always got #(purchases) == 0?

The follow code. I traced "purchases[k] = n" is executed at least once.

But after exit the loop, I always got #(purchases) == 0. Why? How to modify the code?




Code:
function module:MERCHANT_SHOW()
local purchases = {}
for k, v in pairs(self.needs) do
local n = v - GetItemCount(k)
if n > 0 then
purchases[k] = n
end
end

if #(purchases) == 0 then return end
-- other code goes here
end
|||Well, unless I'm mistaken, the # and table.getn (depreciated, but I still use it, *shrug*) will return how many items are in an ordered list. As soon as you throw it out of order, or introduce keys to it, the count will be wrong.

Example:

local list = {};

list[1] = 1;

list[2] = 1;

list[3] = 1;

table.getn(list) or #list will return 3, since the items were added in order.

local list2 = {};

list2["a"] = 1;

list2["b"] = 1;

list2["c"] = 1;

table.getn(list) or #list will return 0, since the item keys are not in order. The order is 1 to n, with no breaks in between, where n is the total number of items. If you throw is text (keys) or out of order numbers, like list2[222] = 1, you won't have an accurate count. Likewise:

local list3 = {};

list3[1] = 1;

list3[2] = 1;

list3[7] = 1;

table.getn(list) or #list will return 2, since it started with 1, then found 2, and when it tried to find 3 and failed, it assumed that there were only 2 items in the list (although there are 3)

I hope that all made sense? The reason why you're getting the issue you're seeing is because you're adding data to the "k" index of the array. Since k could be anything since you're reading from another array, it might not be a number, or in numerical order. It could be a collection of strings.

I might suggest the following:


Code:
function module:MERCHANT_SHOW()
local purchases = {}
local count = 0;
for k, v in pairs(self.needs) do
local n = v - GetItemCount(k)
if n > 0 then
purchases[k] = n
count = count + 1;
end
end

if count == 0 then return end
-- other code goes here
end

Just remember that since there is no numerical order to your purchases table, you'll have to transverse it just like the self.needs table:


Code:
--good code
for k, v in pairs(purchases)
-- code
end

When you need to run through it later. A simple:


Code:
-- bad code
for i = 1, count do
item = purchases[i];
-- code
end

Won't work. I hope this helps you out!

No comments:

Post a Comment