I am working on debugging an algorithm I wrote and part of it has an error that is incomprehensible to me. The only way I discovered it was by printing, because it was not throwing any errors in the output. Before getting to deep into this issue I would like to mention that EgoMoose
already solved my issue by recommending table.sort()
and using both the first and second argument. That being said, I would still like to find out why my function was not working as intended. I don't think that this first function I will post has any relationship to the problem, but I will post it just to make sure (and satisfy the curious among you all). Note: I will likely be changing a lot of these functions because EgoMoose
revealed the incredibly useful second parameter of table.sort()
. I just want to find out the elusive logic error in my code so that I do not repeat it in the future. Here is the first function:
local function findMatches(recipes, inputDictionary) --[[ recipes is an array and I will reveal its structure at the end of this question. inputDictionary is just a dictionary of words retrieved from a lowercased string input by a user. --]] local newRecipeList = {unpack(recipes)} --[[ This is so that I don't mess with the original recipes array. --]] local matchesList = {} for i, recipe in pairs(newRecipeList) do local ingredientsList = recipe.Ingredients --[[ Note: In Lua recipe.Ingredients is the same as recipe["Ingredients"] --]] if ingredientsList then local matchesAmount = 0 for i,v in pairs(ingredientsList) do if inputDictionary[i:lower()] then matchesAmount = matchesAmount + 1 end end if matchesAmount > 0 then recipe["Amount"] = matchesAmount table.insert(matchesList, recipe) end end end return sortByLargest(matchesList) --[[ sortByLargest() is the function that is causing me problems I just wanted to provide this function so that you could see where "array" was coming from. --]] end
As far as I know it is working correctly. The function that causes me the most problems is this one:
local function sortByLargest(array) print(#array) -- this prints 3 local greatestArray = {} while #array > 0 do print("Looped") local indexOfGreatestSoFar, greatestSoFar = next(array) for i,v in pairs(array) do print(v.Amount.." "..v.Name) --[[ The output from these prints is as follows: Looped 1 Beef and Cheese 1 Beef Cheese 1 Beef and flower Looped 1 Beef Cheese 1 Beef and flower Beef and Cheese Beef Cheese As you can see it is only looping twice when #array is 3 --]] if v.Amount > greatestSoFar.Amount then greatestSoFar = v indexOfGreatestSoFar = i end end table.insert(greatestArray, greatestSoFar) array[indexOfGreatestSoFar] = nil end return sortByUpvotes(greatestArray) end
I hope that you can spot some kind of error or something in that function of mine. The structure of the recipes array that is passed as an argument to the recipes parameter is thus:
local exampleListOfRecipeTypes = { { ["Name"] = "Beef and Cheese"; ["Upvotes"] = 0; ["Ingredients"] = { ["Salt"] = "1 tsp"; ["Beef"] = "1 pound"; }; }; { ["Name"] = "Beef Cheese"; ["Upvotes"] = 0; ["Ingredients"] = { ["Salt"] = "1 tsp"; ["Beef"] = "2 pounds"; }; }; { ["Name"] = "Beef and flower"; ["Upvotes"] = 0; ["Ingredients"] = { ["Salt"] = "1 tsp"; }; }; }
I would appreciate any insight on this matter. Note that an alternative solution has already been given by EgoMoose
. I just want to find the elusive logic error in my code. Thanks!
Your problem is this line:
array[indexOfGreatestSoFar] = nil
You're operating on the array part of a Lua table, and the element you are removing (setting to nil) is not the last one, so you're making the array sparse. Neither ipairs nor the # operator are guaranteed to iterate past the first nil value they encounter. In your example, the size of the array as far as # is concerned jumps from 3 to 1.
Because the array you're drawing from is unordered, you can compact on element removal like this:
array[indexOfGreatestSoFar] = array[#array] array[#array] = nil
Locked by User#19524
This question has been locked to preserve its current state and prevent spam and unwanted comments and answers.
Why was this question closed?