Вложенные таблицы и числовые ключи в Lua - PullRequest
3 голосов
/ 19 июня 2011

Я не уверен, возможно ли это из-за числовых индексов, но, надеюсь, кто-то может указать мне правильное направление.

Учитывая таблицу:

t = { 13, 200, 12, 15, 23 }

какМогу ли я вложить таблицу, используя числа?

t["200"] = {"stuff", "more stuff", "even more stuff"}

, похоже, не работает, так как она создаст позицию 200 и заполнит пустые ячейки нулем.Я бы добавил письмо в качестве суффикса / префикса, но проблема заключается в попытке отсортировать таблицу численно.Это вообще возможно, или я застрял с другим методом?Спасибо!

Незначительное редактирование благодаря реализации:

t["200"] = {"stuff", "more stuff", "even more stuff"}

фактически создает ключ "200", тогда как:

t[200] = {"stuff", "more stuff", "even more stuff"}

создает индекс 200 со всемеще ноль.

Ответы [ 3 ]

4 голосов
/ 19 июня 2011

Во-первых, DeadMG верен; Вы использовали строку, а не числовой индекс. Однако, даже если бы вы использовали числовой индекс, это не помогло бы.

Если вы сделаете это:

someTable = {"value1", "value2", {"value3a", "value3b"}};
someTable[50] = {"value50a", "value50b"};

Длина таблицы, #someTable, все равно будет 3 . Зачем? Потому что Lua определяет массивы в таблице на основе смежных элементов. Помните: вы можете получить доступ к любому элементу любой таблицы; все они концептуально заполнены nil, пока вы не дадите им фактическое значение.

Lua определяет длину таблицы как число значений в таблице, если вы начинаете считать с числового индекса 1, пока не достигнете первого значения nil. Поскольку someTable[4] равно нулю, длина равна 3.

Если вы хотите вставить новый элемент в конец таблицы массива, то вы можете сделать это:

someTable[#someTable + 1] = "newValue";

Значение само может быть таблицей:

someTable[#someTable + 1] = {"newValuea", "newValueb"};

Если вы просто спрашиваете, как получить доступ к вложенной таблице, это просто и не имеет ничего общего с ключами, которые вы используете.

В вложенных таблицах нет ничего особенного. Таблицы являются значениями, и записи таблицы могут быть любыми, включая другие таблицы.

Если у вас есть таблица, и вы хотите просмотреть записи массива в ней, вы используете это:

local aTable = {"first", "second", "third", ...}
for i, value in ipairs(aTable) do
    --`value` contains the entries in the table.
end

Вложенная таблица ничем не отличается; это просто вопрос получения таблицы. local nestedTable = {"first", "second", "third", ...} nestedTable [#nestedTable + 1] = {"newFirst", "newSecond", ...} local aTable = nestedTable [#nestedTable]; для i значение в ipairs (aTable) сделать - value содержит записи в таблице. конец

Или вы могли бы просто сделать ipairs(nestedTable[#nestedTable]). Обратите внимание, что конкретный используемый здесь ключ (целочисленное значение) совершенно не важен . Этот ключ мог быть строкой, числом с плавающей точкой, другой таблицей, некоторыми пользовательскими данными и т. Д. Это не имеет значения.

Обратите внимание, что мы используем ipairs, потому что мы хотим перебирать только элементы массива таблицы. Длина массива определена выше. Если бы мы хотели перебрать каждый элемент таблицы, мы бы использовали pairs вместо ipairs. Конечно, pairs выполняет неупорядоченный поиск, поэтому не гарантируется, что он будет в порядке массива.

Если вы хотите рекурсивно найти каждый элемент во вложенной таблице, вы можете сделать это:

local function RecursiveSearch(aTable)
    for key, value in pairs(aTable) do --unordered search
        if(type(value) == "table") do
            RecursiveSearch(value)
        else
            --Do something with this.
        end
    end
end

Обратите внимание, что приведенное выше может выполнять бесконечный цикл, поскольку для таблицы возможно иметь круговые ссылки:

local tableA = {}
local tableB = {tableA}
local tableA[1] = tableB
RecursiveSearch(tableA) --Infinite loop.
3 голосов
/ 19 июня 2011

Возможно, это поможет просмотреть ваше задание следующим образом:

t = { [1] = 13, [2] = 200, [3] = 12, [4] = 15, [5] = 23 }

Чтобы изменить то, что в настоящее время 200 (а именно t[2]), вы делаете:

t[2] = {"stuff", "more stuff", "even more stuff"}

Редактировать: в результате ваша таблица будет выглядеть так:

t = { [1] = 13, [2] = {"stuff", "more stuff", "even more stuff"}, [3] = 12, [4] = 15, [5] = 23 }
-- or, equivalent::
t = { 13, {"stuff", "more stuff", "even more stuff"}, 12, 15, 23 }
1 голос
/ 19 июня 2011

Беда в том, что вы используете "". Ваша таблица t содержит набор чисел , и вы вводите строку в качестве ключа. Вы хотите перебрать таблицу и сделать ... то, что вы не очень хорошо определили. Тем не менее, вы не можете добавить таблицу во время итерации, поэтому вам, возможно, придется сделать несколько забавных вещей.

t = { 13, 200, 12, 15, 23 }
newt = {};
for key, value in pairs(t) {
    newt[value] = { }; 
}

Это создаст запись таблицы в newt, где ключом является значение в таблице t, для всех значений в t.

...