Таблицы. Что это такое и с чем его едят. Часть 1. — различия между версиями
Материал из S.T.A.L.K.E.R. Inside Wiki
(→Обход элементов хэш-таблицы) |
(оформил и сменил категорию..) |
||
(не показана 1 промежуточная версия 1 участника) | |||
Строка 1: | Строка 1: | ||
Итак. Большинство модеров которые начинают осваивать скриптинг сталкера сталкиваются с таким понятием как таблицы. | Итак. Большинство модеров которые начинают осваивать скриптинг сталкера сталкиваются с таким понятием как таблицы. | ||
==Таблицы== | ==Таблицы== | ||
− | Таблица в Lua – это не только базовый тип данных. И даже не столько. Это фундаментальная основа языка, предопределяющая чуть ли не все возможности Lua.<br> | + | Таблица в '''Lua''' – это не только базовый тип данных. И даже не столько. Это фундаментальная основа языка, предопределяющая чуть ли не все возможности Lua.<br> |
Таблицы могут использоваться как обычные массивы, таблицы символов, множества, поля записей, деревья и так далее.<br> | Таблицы могут использоваться как обычные массивы, таблицы символов, множества, поля записей, деревья и так далее.<br> | ||
Причем, поскольку функции относятся к значениям первого класса, поля таблицы могут содержать и функции. Таким образом, таблицы могут хранить методы. | Причем, поскольку функции относятся к значениям первого класса, поля таблицы могут содержать и функции. Таким образом, таблицы могут хранить методы. | ||
Строка 8: | Строка 8: | ||
Например, вычисление знаменитой рекурсивной функции Аккермана на Lua на порядок быстрее, чем на Perl и Ruby, и в пять раз – чем на Python.<br> | Например, вычисление знаменитой рекурсивной функции Аккермана на Lua на порядок быстрее, чем на Perl и Ruby, и в пять раз – чем на Python.<br> | ||
Скорость вычисления хэш-функций (с использованием механизма хэширования и строятся Lua-таблицы) у Lua почти безупречна – интерпретируемые Lua-программы справляются с этой задачей менее чем в два раза медленнее написанных на языке C. | Скорость вычисления хэш-функций (с использованием механизма хэширования и строятся Lua-таблицы) у Lua почти безупречна – интерпретируемые Lua-программы справляются с этой задачей менее чем в два раза медленнее написанных на языке C. | ||
− | |||
+ | ==Определение== | ||
Таблица представляет собой ассоциативный массив (набор пар ключ-значение). Ключём (индексом) и значением может быть любой тип данных, используемых в Lua (за исключением '''nil''').<br> | Таблица представляет собой ассоциативный массив (набор пар ключ-значение). Ключём (индексом) и значением может быть любой тип данных, используемых в Lua (за исключением '''nil''').<br> | ||
Строка 16: | Строка 16: | ||
Поля отделяются друг от друга запятыми ("''','''") или точками с запятой ("''';'''"). При этом допускается наличие разделителя после последнего поля. | Поля отделяются друг от друга запятыми ("''','''") или точками с запятой ("''';'''"). При этом допускается наличие разделителя после последнего поля. | ||
− | Таблица может быть проинициализирована при создании (стандартный конструктор таблицы) : | + | Таблица может быть проинициализирована при создании (стандартный конструктор таблицы): |
+ | <lua>t1 = {} -- пустая таблица | ||
+ | t2 = { 1, 5, 7, 'abc' } -- обычный массив | ||
+ | t3 = { x = 7, y = "6" } -- таблица с именованными полями '''x''' и '''y''' | ||
+ | t4 = { 1, 'string', x = 77 } -- смешанная таблица | ||
+ | t5 = { 1, xxx = 17, } -- разделитель в конце допустим</lua> | ||
− | + | Или заполнена позже, инициализируя каждую пару ключ-значение: | |
− | + | <lua>t4 = {} | |
− | + | t4[1] = 1 -- Определяет число 1 на место, индексируемое номером 1 | |
− | + | t4[2] = 'string' -- Определяет строку 'string' на место, индексируемое номером 2 | |
− | + | t4['x'] = 77 -- Определяет число 77 на место, индексируемое строкой 'x'</lua> | |
− | + | Для удобства работы можно вместо индексирования таблицы по имени (строке) использовать это имя как имя поля структуры: | |
− | + | <lua>t4['x'] = 77 | |
− | + | t4.x = 77</lua> | |
− | + | ||
− | + | ||
− | + | ||
− | + | ||
− | Для удобства работы можно вместо индексирования таблицы по имени (строке) использовать это имя как имя поля структуры : | + | |
− | + | ||
− | + | ||
− | + | ||
Эти две формы обращения полностью эквивалентны. | Эти две формы обращения полностью эквивалентны. | ||
==Массив== | ==Массив== | ||
− | |||
Чтобы получить обычный массив (таблица t2) просто задаются значения элементов. Ключи будут установлены автоматически.<br> | Чтобы получить обычный массив (таблица t2) просто задаются значения элементов. Ключи будут установлены автоматически.<br> | ||
В Lua обычные массивы индексируются целыми, последовательно-нарастающими числами начиная с единицы. | В Lua обычные массивы индексируются целыми, последовательно-нарастающими числами начиная с единицы. | ||
Примеры ниже эквивалентны. | Примеры ниже эквивалентны. | ||
+ | <lua>t2 = { 1, 5, 7, 'abc' } | ||
− | + | t2 = { [1]=1, [2]=5, [3]=7, [4]='abc' } | |
− | + | ||
− | + | ||
− | + | t2 = {} | |
− | + | t2[1] = 1 | |
− | + | t2[2] = 5 | |
− | + | t2[3] = 7 | |
− | + | t2[4] = 'abc'</lua> | |
Пока возможно, Lua внутри себя таблицу хранит как массив, а не как хэш - таблицу.<br> | Пока возможно, Lua внутри себя таблицу хранит как массив, а не как хэш - таблицу.<br> | ||
В этом случае доступ к элементам таблицы происходит почти так же быстро, как в массивах Си. Поэтому без особой нужды не нужно превращать массив в хэш.<br> | В этом случае доступ к элементам таблицы происходит почти так же быстро, как в массивах Си. Поэтому без особой нужды не нужно превращать массив в хэш.<br> | ||
Для того, чтобы не нарушать структуру при добавлении и удалении элементов массива стоит пользоваться библиотекой Lua '''table'''. | Для того, чтобы не нарушать структуру при добавлении и удалении элементов массива стоит пользоваться библиотекой Lua '''table'''. | ||
− | + | <lua>local t = {1, 2, 3, 4, 5} | |
− | + | table.insert(t, 6) -- добавляет элемент в конец массива. t = {1, 2, 3, 4, 5, 6} | |
− | + | table.insert(t, 0, 1) -- вставляет элемент по индексу, сдвигая оставшиеся элементы массива. t = {0, 1, 2, 3, 4, 5, 6} | |
− | + | table.remove(t, 3) -- удаляет из таблицы элемент по индексу 3 и сдвигает оставшиеся элементы. t = {0, 1, 3, 4, 5, 6}</lua> | |
− | + | ||
===Размер массива=== | ===Размер массива=== | ||
Получение размера массива выполняется оператором '''#''': | Получение размера массива выполняется оператором '''#''': | ||
− | + | <lua>local count = #t</lua> | |
− | + | Оператор '''#''' возвращает целое число n, такое, что '''t[n]''' не '''nil''', и '''t[n + 1]''' равно '''nil'''. Другими словами оператор '''#''', возвращает максимальный индекс непрерывной последовательности ключей от начала массива.<br>Соответственно, для таблицы: | |
− | + | <lua>t = {1, [100] = 2}</lua> | |
− | Оператор # возвращает целое число n, такое, что t[n] не nil, и t[n + 1] равно nil. Другими словами оператор #, возвращает максимальный индекс непрерывной последовательности ключей от начала массива.<br>Соответственно, для таблицы: | + | длина будет равна 1, поскольку '''t[1]''' не '''nil''', а '''t[1 + 1]''' равно '''nil'''. |
− | + | Для обычного массива, оператор '''#''' вернет количество элементов в массиве. | |
− | + | ||
− | + | ||
− | длина будет равна 1, поскольку t[1] не nil, а t[1 + 1] равно nil. | + | |
− | Для обычного массива, оператор # вернет количество элементов в массиве. | + | |
===Обход элементов массива=== | ===Обход элементов массива=== | ||
− | |||
Для обхода элементов массива используется как простая, так и расширенная форма записи оператора '''for''' (см. http://www.lua.ru/doc/2.4.5.html ) | Для обхода элементов массива используется как простая, так и расширенная форма записи оператора '''for''' (см. http://www.lua.ru/doc/2.4.5.html ) | ||
− | Обычно применяется '''простая форма''' : | + | Обычно применяется '''простая форма''': |
− | + | <lua>for i=1,#t do | |
− | + | ... | |
− | + | end</lua> | |
− | + | ||
Цикл обойдет все поля массива от поля с индексом 1 (i=1) до последнего индекса поля (#t), определяемого оператором '''#''' (см. "Размер массива")<br> | Цикл обойдет все поля массива от поля с индексом 1 (i=1) до последнего индекса поля (#t), определяемого оператором '''#''' (см. "Размер массива")<br> | ||
− | Или же '''расширенная форма''' с использованием функции-итератора '''ipairs''' : | + | Или же '''расширенная форма''' с использованием функции-итератора '''ipairs''': |
− | + | <lua>for key,value in ipairs(t) do | |
− | + | ... | |
− | + | end</lua> | |
− | + | ||
− | Функция-итератор ipairs возвращает два значения. Первое - ключ этого поля, второе - значение.<br> | + | Функция-итератор '''ipairs''' возвращает два значения. Первое - ключ этого поля, второе - значение.<br> |
При нахождении каждого последующего поля, эти значения присваиваются переменным '''key''' и '''value'''. | При нахождении каждого последующего поля, эти значения присваиваются переменным '''key''' и '''value'''. | ||
==Хэш-таблицы== | ==Хэш-таблицы== | ||
− | + | Талицы, не попадающие под определение массива, являются хэш-таблицами. Индексами таких таблиц являются объекты различных типов (кроме '''nil''').<br> | |
− | Талицы, не попадающие под определение массива, являются хэш-таблицами. Индексами таких таблиц являются объекты различных типов (кроме nil).<br> | + | |
Узнать количество элементов такой таблицы, кроме как обойдя их все, нельзя. | Узнать количество элементов такой таблицы, кроме как обойдя их все, нельзя. | ||
+ | |||
===Строение хэш-таблицы=== | ===Строение хэш-таблицы=== | ||
Любая хэш-таблица состоит из двух частей - индексированной и именованной. | Любая хэш-таблица состоит из двух частей - индексированной и именованной. | ||
Индексированная часть подчиняется законам массива (см. выше), именованная - включает индексы(ключи), которые невозможно включить в индексированную часть, не нарушая её строения. | Индексированная часть подчиняется законам массива (см. выше), именованная - включает индексы(ключи), которые невозможно включить в индексированную часть, не нарушая её строения. | ||
− | Например для таблицы : | + | Например для таблицы: |
− | + | <lua>t = {a=1,b=2}</lua> | |
− | существует индексированная часть. Подтвердить это можно вызвав оператор '#', предназначенный для определения длины : | + | существует индексированная часть. Подтвердить это можно вызвав оператор '#', предназначенный для определения длины: |
− | + | <lua>print(#t) --> 0</lua> | |
− | Т.е. оператор '#' определил (хоть и нулевую, но) длину. Проверив таблицу : | + | Т.е. оператор '#' определил (хоть и нулевую, но) длину. Проверив таблицу: |
− | + | <lua>t = {a=1,b=2, 'one'}</lua> | |
Длина будет равна 1, т.к. появилось поле с индексом - [1], и значением - 'one' (автоматическое назначение индекса. см. выше) | Длина будет равна 1, т.к. появилось поле с индексом - [1], и значением - 'one' (автоматическое назначение индекса. см. выше) | ||
Ни одно из двух других полей этой таблицы не может быть частью массива, вместе с полем [1]='one', т.к. их индексы не соответствуют индексу с номером [2]. | Ни одно из двух других полей этой таблицы не может быть частью массива, вместе с полем [1]='one', т.к. их индексы не соответствуют индексу с номером [2]. | ||
Строка 114: | Строка 101: | ||
===Обход элементов хэш-таблицы=== | ===Обход элементов хэш-таблицы=== | ||
− | |||
Обход осуществляется только '''расширенной формой''' оператора '''for''' с использование функции-итератора '''pairs'''.<br> | Обход осуществляется только '''расширенной формой''' оператора '''for''' с использование функции-итератора '''pairs'''.<br> | ||
− | Эта функция позволяет обойти элементы любых таблиц (включая массивы). Возвращаемые значение такие-же, как и для функции ''ipairs'' : | + | Эта функция позволяет обойти элементы любых таблиц (включая массивы). Возвращаемые значение такие-же, как и для функции ''ipairs'': |
− | + | <lua>for k,v in pairs(t) do | |
− | + | ... | |
− | + | end</lua> | |
− | + | ||
При этом '''всегда''' сначала определяются поля индексированной части как массива, а затем именованной. | При этом '''всегда''' сначала определяются поля индексированной части как массива, а затем именованной. | ||
Строка 128: | Строка 113: | ||
Хотя лично я не согласен с утверждением, что "ни при каких обстоятельствах не используйте внутри этого цикла удаление/добавление строк" и "следует использовать только для операций, не изменяющих структуру изменяемой таблицы!". | Хотя лично я не согласен с утверждением, что "ни при каких обстоятельствах не используйте внутри этого цикла удаление/добавление строк" и "следует использовать только для операций, не изменяющих структуру изменяемой таблицы!". | ||
Правильнее было бы сказать, что "ни при каких обстоятельствах не изменяйте длину массива внутри этого цикла". | Правильнее было бы сказать, что "ни при каких обстоятельствах не изменяйте длину массива внутри этого цикла". | ||
− | Т.е. "смертельный" вариант : | + | Т.е. "смертельный" вариант: |
+ | <lua>for i = i, #t do | ||
+ | table.remove(t,i) | ||
+ | end</lua> | ||
− | + | в, котором с каждым "оборотом" уменьшается длина массива, становится самым быстрым и оптимальным в случае...ну, например, реверсирования массива: | |
− | + | <lua>local len=#t | |
− | + | for i = len-1, 1, -1 do | |
− | + | t[len] = table.remove(t,i) | |
− | в, котором с каждым "оборотом" уменьшается длина массива, становится самым быстрым и оптимальным в случае...ну, например, реверсирования массива : | + | end</lua> |
− | + | ||
− | + | ||
− | + | ||
− | + | ||
в котором длина массива не изменяется. | в котором длина массива не изменяется. | ||
''to be continue ...'' | ''to be continue ...'' | ||
− | ''' | + | '''Nazgool''' |
P.S. То, что ниже, это остатки первоначальной статьи, верхнюю часть которой я безжалостно вырезал за несоответствие названию статьи. | P.S. То, что ниже, это остатки первоначальной статьи, верхнюю часть которой я безжалостно вырезал за несоответствие названию статьи. | ||
Строка 150: | Строка 134: | ||
К примеру: | К примеру: | ||
+ | <lua>local variables = {1, 2}</lua> | ||
− | + | ''Примечание'': таблицы можно использовать как за функцией, так и внутри неё. | |
− | + | ||
− | Примечание: таблицы можно использовать как за функцией, так и внутри неё. | + | |
В нашем случае таблица содержит набор чисел 1 и 2. Что же с ними можно сделать? | В нашем случае таблица содержит набор чисел 1 и 2. Что же с ними можно сделать? | ||
+ | <lua>function table() | ||
+ | local variables= {1, 2} --наша таблица | ||
+ | rezultat = variables[math.random(table.getn(variables))] --rezultat локальная переменная. | ||
+ | if rezultat == 1 then | ||
+ | news_manager.send_tip(db.actor,lose_text, nil, nil, 10000) and db.actor:give_info_portion("lose") | ||
+ | end | ||
+ | if rezultat == 2 then | ||
+ | news_manager.send_tip(db.actor,win_text, nil, nil, 10000) and db.actor:give_info_portion("win") | ||
+ | end | ||
+ | end</lua> | ||
− | + | Поясню: '''variables[math.random(table.getn(variables))]''' этот оператор позволяет взять рандомное значение из данной таблицы. Тобишь случайно взять либо число 1, либо число 2. | |
− | + | <lua>if rezultat == 1 then | |
− | + | news_manager.send_tip(db.actor,lose_text, nil, nil, 10000) and db.actor:give_info_portion("lose") | |
− | + | end | |
− | + | if rezultat == 2 then | |
− | + | news_manager.send_tip(db.actor,win_text, nil, nil, 10000) and db.actor:give_info_portion("win") | |
− | + | end</lua> | |
− | + | ||
− | Поясню: variables[math.random(table.getn(variables))] этот оператор позволяет взять рандомное значение из данной таблицы. Тобишь случайно взять либо число 1, либо число 2. | + | |
− | + | ||
− | + | ||
− | + | ||
− | + | ||
− | + | ||
Определяет значение взятое из таблицы, и в зависимости от результата присылает нам то или иное сообщение (news_manager.send_tip(db.actor,***, nil, nil, 10000)) и даёт тот или иной инфопоршень (db.actor:give_info_portion("***") end). | Определяет значение взятое из таблицы, и в зависимости от результата присылает нам то или иное сообщение (news_manager.send_tip(db.actor,***, nil, nil, 10000)) и даёт тот или иной инфопоршень (db.actor:give_info_portion("***") end). | ||
− | '''==''' | + | '''==''' - это оператор сравнения. В нашем случае это "равно". Так же есть операторы: |
− | + | ||
− | + | ||
'''>''' - больше. | '''>''' - больше. | ||
Строка 191: | Строка 175: | ||
На этом примере вы можете создать простейшую функцию спауна: | На этом примере вы можете создать простейшую функцию спауна: | ||
+ | <lua>local stalker_types = {"bread", "kolbasa", "conserva", "vodka"} | ||
− | + | function spawn_item() | |
− | + | alife():create(stalker_types[math.random(4)],vector():set(-0.112,0.477,-215.563),174943,265) | |
− | + | end</lua> | |
− | + | ||
− | + | ||
Как видите таблица используется вне функции, но можно и в самой функции. В данном примере в определённой точке с координатами (-0.112,0.477,-215.563),174943,265) заспаунится определённый предмет из списка. В эту таблицу можно внести как сталкеров, так и мутантов. | Как видите таблица используется вне функции, но можно и в самой функции. В данном примере в определённой точке с координатами (-0.112,0.477,-215.563),174943,265) заспаунится определённый предмет из списка. В эту таблицу можно внести как сталкеров, так и мутантов. | ||
− | ''' | + | Автор: '''iDreD aka кровоSTALKER.''' |
− | [[Категория: | + | [[Категория: Скрипты]] |
Текущая версия на 12:34, 23 сентября 2014
Итак. Большинство модеров которые начинают осваивать скриптинг сталкера сталкиваются с таким понятием как таблицы.
Содержание
Таблицы
Таблица в Lua – это не только базовый тип данных. И даже не столько. Это фундаментальная основа языка, предопределяющая чуть ли не все возможности Lua.
Таблицы могут использоваться как обычные массивы, таблицы символов, множества, поля записей, деревья и так далее.
Причем, поскольку функции относятся к значениям первого класса, поля таблицы могут содержать и функции. Таким образом, таблицы могут хранить методы.
Механизмы реализации типа «таблица» или ассоциативный массив в Lua очень эффективны.
Например, вычисление знаменитой рекурсивной функции Аккермана на Lua на порядок быстрее, чем на Perl и Ruby, и в пять раз – чем на Python.
Скорость вычисления хэш-функций (с использованием механизма хэширования и строятся Lua-таблицы) у Lua почти безупречна – интерпретируемые Lua-программы справляются с этой задачей менее чем в два раза медленнее написанных на языке C.
Определение
Таблица представляет собой ассоциативный массив (набор пар ключ-значение). Ключём (индексом) и значением может быть любой тип данных, используемых в Lua (за исключением nil).
Конструктор таблицы
Конструктор используется для создания таблиц и представляет собой список полей в фигурных скобках.
Поля отделяются друг от друга запятыми (",") или точками с запятой (";"). При этом допускается наличие разделителя после последнего поля.
Таблица может быть проинициализирована при создании (стандартный конструктор таблицы):
t1 = {} -- пустая таблица t2 = { 1, 5, 7, 'abc' } -- обычный массив t3 = { x = 7, y = "6" } -- таблица с именованными полями '''x''' и '''y''' t4 = { 1, 'string', x = 77 } -- смешанная таблица t5 = { 1, xxx = 17, } -- разделитель в конце допустим
Или заполнена позже, инициализируя каждую пару ключ-значение:
t4 = {} t4[1] = 1 -- Определяет число 1 на место, индексируемое номером 1 t4[2] = 'string' -- Определяет строку 'string' на место, индексируемое номером 2 t4['x'] = 77 -- Определяет число 77 на место, индексируемое строкой 'x'
Для удобства работы можно вместо индексирования таблицы по имени (строке) использовать это имя как имя поля структуры:
t4['x'] = 77 t4.x = 77
Эти две формы обращения полностью эквивалентны.
Массив
Чтобы получить обычный массив (таблица t2) просто задаются значения элементов. Ключи будут установлены автоматически.
В Lua обычные массивы индексируются целыми, последовательно-нарастающими числами начиная с единицы.
Примеры ниже эквивалентны.
t2 = { 1, 5, 7, 'abc' } t2 = { [1]=1, [2]=5, [3]=7, [4]='abc' } t2 = {} t2[1] = 1 t2[2] = 5 t2[3] = 7 t2[4] = 'abc'
Пока возможно, Lua внутри себя таблицу хранит как массив, а не как хэш - таблицу.
В этом случае доступ к элементам таблицы происходит почти так же быстро, как в массивах Си. Поэтому без особой нужды не нужно превращать массив в хэш.
Для того, чтобы не нарушать структуру при добавлении и удалении элементов массива стоит пользоваться библиотекой Lua table.
local t = {1, 2, 3, 4, 5} table.insert(t, 6) -- добавляет элемент в конец массива. t = {1, 2, 3, 4, 5, 6} table.insert(t, 0, 1) -- вставляет элемент по индексу, сдвигая оставшиеся элементы массива. t = {0, 1, 2, 3, 4, 5, 6} table.remove(t, 3) -- удаляет из таблицы элемент по индексу 3 и сдвигает оставшиеся элементы. t = {0, 1, 3, 4, 5, 6}
Размер массива
Получение размера массива выполняется оператором #:
local count = #t
Оператор # возвращает целое число n, такое, что t[n] не nil, и t[n + 1] равно nil. Другими словами оператор #, возвращает максимальный индекс непрерывной последовательности ключей от начала массива.
Соответственно, для таблицы:
t = {1, [100] = 2}
длина будет равна 1, поскольку t[1] не nil, а t[1 + 1] равно nil. Для обычного массива, оператор # вернет количество элементов в массиве.
Обход элементов массива
Для обхода элементов массива используется как простая, так и расширенная форма записи оператора for (см. http://www.lua.ru/doc/2.4.5.html ) Обычно применяется простая форма:
for i=1,#t do ... end
Цикл обойдет все поля массива от поля с индексом 1 (i=1) до последнего индекса поля (#t), определяемого оператором # (см. "Размер массива")
Или же расширенная форма с использованием функции-итератора ipairs:
for key,value in ipairs(t) do ... end
Функция-итератор ipairs возвращает два значения. Первое - ключ этого поля, второе - значение.
При нахождении каждого последующего поля, эти значения присваиваются переменным key и value.
Хэш-таблицы
Талицы, не попадающие под определение массива, являются хэш-таблицами. Индексами таких таблиц являются объекты различных типов (кроме nil).
Узнать количество элементов такой таблицы, кроме как обойдя их все, нельзя.
Строение хэш-таблицы
Любая хэш-таблица состоит из двух частей - индексированной и именованной. Индексированная часть подчиняется законам массива (см. выше), именованная - включает индексы(ключи), которые невозможно включить в индексированную часть, не нарушая её строения. Например для таблицы:
t = {a=1,b=2}
существует индексированная часть. Подтвердить это можно вызвав оператор '#', предназначенный для определения длины:
print(#t) --> 0
Т.е. оператор '#' определил (хоть и нулевую, но) длину. Проверив таблицу:
t = {a=1,b=2, 'one'}
Длина будет равна 1, т.к. появилось поле с индексом - [1], и значением - 'one' (автоматическое назначение индекса. см. выше) Ни одно из двух других полей этой таблицы не может быть частью массива, вместе с полем [1]='one', т.к. их индексы не соответствуют индексу с номером [2]. Поэтому :
- часть 'one' будет индексированной частью.
- часть a=1 и b=2 именованной
Обход элементов хэш-таблицы
Обход осуществляется только расширенной формой оператора for с использование функции-итератора pairs.
Эта функция позволяет обойти элементы любых таблиц (включая массивы). Возвращаемые значение такие-же, как и для функции ipairs:
for k,v in pairs(t) do ... end
При этом всегда сначала определяются поля индексированной части как массива, а затем именованной.
Об ошибках, связанных с циклами по таблицам см. в статье KamikaZze здесь
Хотя лично я не согласен с утверждением, что "ни при каких обстоятельствах не используйте внутри этого цикла удаление/добавление строк" и "следует использовать только для операций, не изменяющих структуру изменяемой таблицы!". Правильнее было бы сказать, что "ни при каких обстоятельствах не изменяйте длину массива внутри этого цикла". Т.е. "смертельный" вариант:
for i = i, #t do table.remove(t,i) end
в, котором с каждым "оборотом" уменьшается длина массива, становится самым быстрым и оптимальным в случае...ну, например, реверсирования массива:
local len=#t for i = len-1, 1, -1 do t[len] = table.remove(t,i) end
в котором длина массива не изменяется.
to be continue ...
Nazgool
P.S. То, что ниже, это остатки первоначальной статьи, верхнюю часть которой я безжалостно вырезал за несоответствие названию статьи.
К примеру:
local variables = {1, 2}
Примечание: таблицы можно использовать как за функцией, так и внутри неё. В нашем случае таблица содержит набор чисел 1 и 2. Что же с ними можно сделать?
function table() local variables= {1, 2} --наша таблица rezultat = variables[math.random(table.getn(variables))] --rezultat локальная переменная. if rezultat == 1 then news_manager.send_tip(db.actor,lose_text, nil, nil, 10000) and db.actor:give_info_portion("lose") end if rezultat == 2 then news_manager.send_tip(db.actor,win_text, nil, nil, 10000) and db.actor:give_info_portion("win") end end
Поясню: variables[math.random(table.getn(variables))] этот оператор позволяет взять рандомное значение из данной таблицы. Тобишь случайно взять либо число 1, либо число 2.
if rezultat == 1 then news_manager.send_tip(db.actor,lose_text, nil, nil, 10000) and db.actor:give_info_portion("lose") end if rezultat == 2 then news_manager.send_tip(db.actor,win_text, nil, nil, 10000) and db.actor:give_info_portion("win") end
Определяет значение взятое из таблицы, и в зависимости от результата присылает нам то или иное сообщение (news_manager.send_tip(db.actor,***, nil, nil, 10000)) и даёт тот или иной инфопоршень (db.actor:give_info_portion("***") end).
== - это оператор сравнения. В нашем случае это "равно". Так же есть операторы:
> - больше.
< - меньше.
>= - больше или равно.
<= - меньше или равно.
~= - не равно.
Сравнивать можно только числа или локальные переменные с присвоенными к ним числами.
На этом примере вы можете создать простейшую функцию спауна:
local stalker_types = {"bread", "kolbasa", "conserva", "vodka"} function spawn_item() alife():create(stalker_types[math.random(4)],vector():set(-0.112,0.477,-215.563),174943,265) end
Как видите таблица используется вне функции, но можно и в самой функции. В данном примере в определённой точке с координатами (-0.112,0.477,-215.563),174943,265) заспаунится определённый предмет из списка. В эту таблицу можно внести как сталкеров, так и мутантов.
Автор: iDreD aka кровоSTALKER.