Перейти к контенту

Скриптование


Svoboда

Рекомендуемые сообщения

Извиняюсь за свой предыдущий неясный ответ (чего то нашло).

Если жизнь бюрера будет меньше 30, то код ниже (а значит и дроп) не сработает.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

Artos

Тот код-то рабочий. Но вот и с твоим кодом нарвётся человек на random, который не пропустит, и будет говорить что твой вариант не годится :-)

Я хочу гарантированно показать дроп, независимо от того бюрер это или какая другая тварь. А там пусть и с random-ом экспериментирует.

Поделиться этим сообщением


Ссылка на сообщение

PavelSnork

Про статики не буду говорить, т.к. в них я плаваю стилем топора.

А вот про составление кода могу поболтать...

Твои проверки в функции

check_params() не очень оптимальны.

На скорую руку хотел посоветовать избавиться от лишних проверок, используя код типа :

function check_params()
  --/ health
    local iHealth = db.actor.health
    local sHealth_Level
    if iHealth > 0.97 then
        sHealth_Level = "health_level_24"
    elseif iHealth > 0.94 then
        sHealth_Level = "health_level_23"
    elseif iHealth > 0.9  then
        sHealth_Level = "health_level_22"
    elseif iHealth > 0.86 then
        sHealth_Level = "health_level_21"
    elseif iHealth > 0.82 then
        sHealth_Level = "health_level_20"
    elseif iHealth > 0.77 then
        sHealth_Level = "health_level_19"
    elseif iHealth > 0.73 then
        sHealth_Level = "health_level_18"
    elseif iHealth > 0.69 then
        sHealth_Level = "health_level_17"
    elseif iHealth > 0.65 then
        sHealth_Level = "health_level_16"
    elseif iHealth > 0.61 then
        sHealth_Level = "health_level_15"
    elseif iHealth > 0.57 then
        sHealth_Level = "health_level_14"
    elseif iHealth > 0.53 then
        sHealth_Level = "health_level_13"
    elseif iHealth > 0.49 then
        sHealth_Level = "health_level_12"
    elseif iHealth > 0.45 then
        sHealth_Level = "health_level_11"
    elseif iHealth > 0.41 then
        sHealth_Level = "health_level_10"
    elseif iHealth > 0.36 then
        sHealth_Level = "health_level_9"
    elseif iHealth > 0.32 then
        sHealth_Level = "health_level_8"
    elseif iHealth > 0.28 then
        sHealth_Level = "health_level_7"
    elseif iHealth > 0.24 then
        sHealth_Level = "health_level_6"
    elseif iHealth > 0.2  then
        sHealth_Level = "health_level_5"
    elseif iHealth > 0.16 then
        sHealth_Level = "health_level_4"
    elseif iHealth > 0.12 then
        sHealth_Level = "health_level_3"
    elseif iHealth > 0.08 then
        sHealth_Level = "health_level_2"
    elseif iHealth > 0.04 then
        sHealth_Level = "health_level_1"
    end
.... и т.д.

 

Но и этот вариант хоть по скорости и "реальному состоянию ГГ" лучше твоего, но неравномерность нагрузки мне не нравиться.

Поясню.

Скорость выигрывается только за счет удаления лишних проверок.

Теперь о "реальном состоянии ГГ".

 

В твоём коде самые быстрые проверки (первые 3-5) приходятся на то, когда у ГГ здоровье ниже четверти.

Мало кто допускает такое состояние на долгое время. И в основном всю игру держат здоровье в пределах, близких к максимальному.

Мой код как раз и учитывает такое состояние вещей, и самые быстрые проверки придутся как раз на высокий показатель здоровья.

 

Но если такой код (или множество подобных кодов) поставить скажем на апдейт, то можно получить плавающую нагрузку на систему.

И не известно к чему такие пики могут привести.

Например в моём коде при малом количестве здоровья будут произведены практически все сравнения, в то время как при большом только 3 -5 первых.

Разница в количестве операций очевидна.

 

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

Например по принципу "Поиск льва в Африке" (делим Африку пополам,...,потом оставшуюся часть ещё пополам. И в конце концов найдём) :

function check_params()
  --/ health
    local iHealth = db.actor.health
    local sHealth_Level
    if iHealth > 0.53 then
        if iHealth > 0.77 then
            if iHealth > 0.9  then
                if iHealth > 0.94 then
                    if iHealth > 0.97 then
                        sHealth_Level = "health_level_24"
                    else
                        sHealth_Level = "health_level_23"
                    end
                else
                    sHealth_Level = "health_level_22"
                end
            elseif iHealth > 0.82 then
                if iHealth > 0.86 then
                    sHealth_Level = "health_level_21"
                else
                    sHealth_Level = "health_level_20"
                end
            else
                sHealth_Level = "health_level_19"
            end
        elseif iHealth > 0.65 then
            if iHealth > 0.69 then
                if iHealth > 0.73 then
                    sHealth_Level = "health_level_18"
                else
                    sHealth_Level = "health_level_17"
                end
            else
                sHealth_Level = "health_level_16"
            end
        elseif iHealth > 0.57 then
            if iHealth > 0.61 then
                sHealth_Level = "health_level_15"
            else
                sHealth_Level = "health_level_14"
            end
        else
            sHealth_Level = "health_level_13"
        end
    elseif iHealth > 0.28 then
        if iHealth > 0.41 then
            if iHealth > 0.45 then
                if iHealth > 0.49 then
                    sHealth_Level = "health_level_12"
                else
                    sHealth_Level = "health_level_11"
                end
            else
                sHealth_Level = "health_level_10"
            end
        elseif iHealth > 0.32 then
            if iHealth > 0.36 then
                sHealth_Level = "health_level_9"
            else
                sHealth_Level = "health_level_8"
            end
        else
            sHealth_Level = "health_level_7"
        end
    elseif iHealth > 0.16 then
        if iHealth > 0.20 then
            if iHealth > 0.24 then
                sHealth_Level = "health_level_6"
            else
                sHealth_Level = "health_level_5"
            end
        else
            sHealth_Level = "health_level_4"
        end
    elseif iHealth > 0.12 then
        sHealth_Level = "health_level_3"
    elseif iHealth > 0.08 then
        sHealth_Level = "health_level_2"
    elseif iHealth > 0.04 then
        sHealth_Level = "health_level_1"
    end

 

В этом случае нагрузка становиться практически одинаковой при любом показателе, т.к. для поиска совпадения для любого состояния здоровья производиться примерно 5 шагов.

(на последней проверке 6, но это из-за лени :-))

 

 

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

Vano_Santuri

Таблицу из строки сделать не сложно. Желательно знать из строки какого вида?

Например :

local t = {}
local s = "word_1 word_2 word_3 word_4 word_5"
for w in s:gmatch("[%w%_]+") do
    t[#t+1] = w
end

Только вот до сих пор не пойму что же именно тебе нужно? В теме "Lua..." у тебя были одни условия, тут несколько другие.

Объясни подробнее.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение
Desertir, например :
function IsAllNumber(t)
    local i=#t+1
    repeat i=i-1
    until type(t[i])~='number'
    return i==0
end
      
if IsAllNumber(tbl) then
...
end

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

Смотри таблицу математических функций luа - mаth.

Р.S. Прочитай чуть выше, что написал Аrtоs (синим таким)

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

Shadows

function CutWpn(name)
    return name:match('wpn_(.+)') or name
end

spawn_item_in_inv(CutWpn('wpn_ak47'))

Т.е. любое оружие с префиксом wpn_ "прогоняешь" через эту функцию.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

_Призрак_

Из Lua никак не узнаешь.

Дело в том, что функции в Lua (как и table, thread и userdata ) являются так называемыми "first class" объектами, и они не имеют фиксированного имени.

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

Ну например для какой-то функции у тебя существует 3 имени. И есть, тоже например, функция, которая должна определить имя. Какое имя из двух оставшихся она должна возвратить???

Подходящее имя для функции попадает в стек только при её вызове. И вот тут уже можно определить и её имя, и имена всех функций вызвавших данную, т.к. они тоже уже находятся на стеке.

Для этого используется функция debug.getinfo . Например :

function f1(stack_level)
    f2(stack_level)
end

function f2(stack_level)
    f3(stack_level)
end

function f3(stack_level)
    local t = debug.getinfo(stack_level)
    print(t.name)
end

f1(0) --> getinfo
f1(1) --> f3
f1(2) --> f2
f1(3) --> f1

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

RvP

Не стОит заниматься селекционным выведением в инкубаторных условиях. Твой вариант найдет оба имени. Какое из них будет "настоящим"? Да никакое. Это синонимы. Как минимум нужно соблюдать следующие условия :

1. В глобальном пространстве имен должно быть только одно имя для функции. Иначе найдутся и остальные.

2. Из первого следует что синонимы должны быть локальны. А это значит что использовать поиск нужно только в области видимости

этой локальной переменной.

3. Добавь сюда итерацию по всей _G, в отличии от простого и быстрого доступа по ключу, и ...

"Жизнь" подобного варианта нужно будет поддерживать искусственно.

Поделиться этим сообщением


Ссылка на сообщение

serega-gamer

Moжет что-то типа такого подойдёт? :

Я тут добавил и сообщение при восстановления костюма(если нужно конечно)

local hev_crash = "%c[255,160,160,160]Автоматическая система ввода медицинских препаратов\\n".."%c[default] %c[255,230,0,0]Общий сбой системы. Система отключается!"
local hev_restore = "%c[255,160,160,160]Автоматическая система ввода медицинских препаратов\\n".."%c[default] %c[255,230,0,0]Работа системы восстановлена. Система включается!"
local hev_min_cond_active = 0.01
local flag

local   function GetHevParam(hev)
            return hev:condition() < hev_min_cond_active and hev:section() == "nano_kostum"
        end

local   function ShowHevGameNews(msg, path)
            local snd_obj = xr_sound.get_safe_sound_object(path)
            snd_obj:play_no_feedback(db.actor, sound_object.s2d, 0, vector(), 1.0)
            db.actor:give_game_news(msg, "ui\\ui_iconsTotal", Frect():set(0,188,83,47), 0, 3000)
        end

function CheckHevCond()
    local act_suit = db.actor:item_in_slot(6)
    if not flag then
        if  act_suit and GetHevParam(act_suit) then
            ShowHevGameNews(hev_crash, 'HEV\\hev_crash')
            flag = true
        end
    elseif act_suit and not GetHevParam(act_suit) then
        ShowHevGameNews(hev_restore, 'HEV\\hev_restore')
        flag = nil
    end
end

CheckHevCond() на апдейт. Ну и задержку, если нужно

 

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение

iDreD

local t = { wpn_ak74_m1       = true,
            wpn_abakan_m1     = true,
            wpn_ak74u_m1      = true,
            wpn_mp5_m1        = true,
            wpn_groza_m1      = true,
            wpn_spas12_m1     = true,
            wpn_winchester_m1 = true,
            wpn_l85_m1        = true,
            wpn_lr300_m1      = true,
            wpn_svd_m1        = true,
            wpn_sig_m1        = true,
            wpn_val_m1        = true,
            wpn_mp5_m2        = true,
            wpn_abakan_m2     = true,
            wpn_l85_m2        = true,
            wpn_sig_m2        = true,
            wpn_rg6_m1        = true,
            hunters_toz       = true,
            pri_lom_ak74      = true,
            wpn_vintorez_coll = true
          }

function repair_precond_s2()
    local item_in_slot_2 = db.actor:item_in_slot(2)
    if item_in_slot_2 then
        item = item_in_slot_2:section()
        return t[item] and 1 > item_in_slot_2:condition() + 0.01
    end
    return
end

 

Oсмелюсь все же предложить для подобных проверок (прекондишенов) организовать возврат только булевых значений (true|false), что порой критично, т.е. типа:

 ...
function repair_precond_s2()
    local item_in_slot_2 = db.actor:item_in_slot(2)
    if item_in_slot_2 then
        return ( t[item_in_slot_2:section()] == true and 1 > item_in_slot_2:condition() + 0.01 )
    end
    return false
end

--/Artos

Изменено пользователем Artos

Поделиться этим сообщением


Ссылка на сообщение

Artos

Если бы я знал что это должно быть критично, то может быть написал бы так (как вариант) :

function repair_precond_s2()
    local item_in_slot_2 = db.actor:item_in_slot(2)
    local item = item_in_slot_2 and item_in_slot_2:section()
    return t[item] and 1 > item_in_slot_2:condition() + 0.01 or false
end

 

Поделиться этим сообщением


Ссылка на сообщение

Dennis_Chikin, Artos

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

Мне кажется, что если Вы ищите среди множества записей в исходной строке (и искомым разделителем есть символ точки, как определяющий модуль и объект), а также разделителем выражений в подобных строках , как правило, является символ пробела, то...

Если я всё не правильно понял, то можете и не пояснять. Просто в моём понимании на данный момент я бы использовал паттерен :

... func:match('%S+%.%S+')

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

Ну а если я ошибаюсь, то составлял бы искомую строку таким образом, чтобы она работала в унисон с подобным паттерном.

Сразу прошу знающих людей пояснить, - "В чём я не прав?"

С одной стороны кажется дико, что изначально хочу составлять строку. А затем к ней использовать, пусть и быстрый, паттерн. Паттерн ведь составить проще и динамичнее.

Но с другой стороны иного поведения я ещё не встречал. Сложный паттерн заметнее тормозит, по сравнению со "сложной"(???) строкой.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение
а только для строки, состояшей из имени скрипта и имени функции. Т.к. эти имена не могут (не должны) содержать ничего кроме латиницы, цифр и некоторых символов пунктуации (типа '_','-')

Вот это я имел в виду. Если изначально составить строку как нужно...

То они и не будут содержать...

А значит и паттерн...

А в общем прошу прощения, т.к : P.S.

2Всем. В силу всего услышанного о "псевдо"классах в lua, и их несостоятельности, не стану скорее всего выкладывать наработки таймеров. А то забьют на.

2Artos

На днях отдам их тебе(есть пару тонкостей - нужно доработать). Если посчитаешь нужным, и, я так надеялся, таймеры окажутся действительно полезными, то... Дай то Бог.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение
1. Как надо записать ф-ции в таблицу, чтобы можно было их потом вызвать?

Например:

...

[12] = func() spawn(),

...

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

Объясни детальнее чего ты хочешь, может и решение изменится.

Поделиться этим сообщением


Ссылка на сообщение

SkyLoader

1

my_func1 = function() return 1 end
my_func2 = function() return 2 end
my_func3 = function() return 3 end

my_table = {
  [12] = {my_func2, my_func3}, -- заключить линки на функции в таблицы
  [21] = {my_func1, my_func2, my_func3},
  [33] = {my_func3, my_func1}
}

for k,v in pairs(my_table) do -- где-то парсим
    if any_time == k then -- если время совпало с ключем...
        for i=1,#v do
            v[i]() -- вызываем каждую из функций таблицы функций
        end
    end
end

2

four_table = {3,4,5} -- таблицу задавать только глобально в текущем контексте
                     -- при локальном объявлении нужно использовать debug
local t = "four_table"

for k,v in pairs(_G[t]) do -- если таблица находится в глобальном контексте
                           -- если в модуле, то вместо _G[t] пиши имя_файла[t]
    -- action
end

Поделиться этим сообщением


Ссылка на сообщение
На викисталкере есть такая функция:

...бла-бла

Куда ее нужно вставить чтобы она заработала ?

По-моему ерунда полная. В аргументах этой функции нужно задавать практически всё, что и при существующей форме заполнения. Но... велика вероятность ошибки. Перепутать и забыть что-то очень легко. Например обязательное заполнение аргументов значениями? А если потом нужно будет найти откуда ноги растут?

У разрабов по крайней мере всё хоть и просто, но понятно. Нужно что-то задать - присваиваешь по ключу и все дела.

Изменено пользователем Gun12

Поделиться этим сообщением


Ссылка на сообщение
  • Недавно просматривали   0 пользователей

    • Ни один зарегистрированный пользователь не просматривает эту страницу.
×
×
  • Создать...