Запустить скрипт Lua другим скриптом

Страницы: 1
RSS
Запустить скрипт Lua другим скриптом, Запустить скрипт Lua другим скриптом
 
Возможно ли с помощью одного скрипта запустить другой ?
 
Нет
 
Вы имеете ввиду что-то, отличное от Lua команды dofile?
 
Цитата
funduk написал:
Вы имеете ввиду что-то, отличное от Lua команды dofile?
Я имею ввиду - "Возможно ли с помощью одного Lua скрипта, запустить другой ?"
То есть один Kua скрипт запущенный в цикле проверял бы если другой Lua скрипт не запущен - то запустить его.
 
Нет, штатных средств для этого нет.
 

Разбираясь в работе Quik и функциональных возможностях Lua, иногда можно запутаться, и тогда трезвый взгляд со стороны помогает всё расставить по местам. Для меня таким взглядом всегда был Nikolay. И сейчас я бы не стал вмешиваться в эту дискуссию, если бы не ответы!

Да, это возможно! В Lua действительно можно запустить другой Lua-скрипт с помощью функций dofile или loadfile. Вы можете создать основной скрипт, который будет проверять, запущен ли другой скрипт, и если нет — запускать его. Все это и так явно.

Но почему бы не пойти дальше? Хочу озвучить другой подход.

Давайте забудем про все языки (Си, C#, да и про Fortran с Basic я забыл ещё со студенческих времён). Что у нас есть?

  • API Quik: разработчики любезно предоставили нам возможность через Lua получать данные от брокера и отправлять приказы (заявки) брокеру.

  • Функционал Lua: вот здесь начинается самое интересное!

Представим, что поток main — это основной поток (другого ничего нет), в котором всё крутится (в этом легко убедиться, запустив его без задержек).
Функционал Lua предоставляет лёгкие потоки, которые работают внутри основного потока — они называются корутины.

Что они делают? Любые программы, блоки, модули, функции — всё это можно запускать в корутинах! Причём не только последовательно, но и асинхронно.

Таким образом, функция main(), будучи запущенной, превращается в сложнейшую программу, способную не только явно но и в фоновом режиме выполнять что угодно: получать данные, проводить расчёты, подключать и останавливать модули и многое другое.

К чему я так подробно рассказываю? Напишите в своей программе модуль на Lua (это та же таблица)  который хотите запустить, и используйте его где угодно.

Это открывает огромные возможности для создания гибких и мощных решений.

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

Да, такой подход возможен. Но это не то же самое. Понимая, что прямой вариант невозможен, можно попробовать решить через второй вариант. Но он не всегда применим, т.к. есть скрипты не с открытым кодом, с сложным окружением и т.д. Любители использования dofile могут попробовать запустить так два модуля, использующих переменные с одинаковым именованием.

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

При этом обмен данными между скриптами сделать можно. А значит существует и третий подход - это иметь два контура в контролируемых скриптах: холостой и рабочий. Тогда скрипт будет отдельной сущностью, его можно отдельно запустить в терминале. Скрипты постоянно работают, но переходят в разные состояния по командам из контролирующего скрипта, через обмен данными. В таком подходе важно обеспечить перехват ошибок, чтобы контролируемый скрипт не "упал". Но опять же - необходимо иметь открытый код скриптов.
 
Nikolay,  Согласен, вопрос составлен не четко, двусмысленно. Но ведь он звучит все таки так:
Цитата
Saturn написал:
То есть один Kua скрипт запущенный в цикле проверял бы если другой Lua скрипт не запущен - то запустить его.
Ответ: Да, это возможно. В Lua можно запустить другой Lua-скрипт с помощью функции dofile или loadfile. Вы можете создать основной скрипт, который будет проверять, запущен ли другой скрипт, и если нет, то запускать его.
Вот такого подхода пример:
Код
-- основной скрипт (main.lua)
local is_other_script_running = false
-- Функция для проверки, запущен ли другой скрипт
function check_if_other_script_running()
    -- Здесь можно реализовать проверку, например, через файл или глобальную переменную
    -- В данном примере просто используем переменную для демонстрации
    return is_other_script_running
end
-- Функция для запуска другого скрипта
function run_other_script()
    is_other_script_running = true
    dofile("other_script.lua")  -- Запуск другого скрипта
    is_other_script_running = false
end
-- Основной цикл
while true do
    if not check_if_other_script_running() then
        print("Другой скрипт не запущен, запускаю...")
        run_other_script()
    else
        print("Другой скрипт уже запущен.")
    end

    -- Пауза перед следующей проверкой
    os.execute("sleep 1")  -- Для Linux/MacOS
    -- os.execute("timeout /t 1")  -- Для Windows
end
Никаких принципиальных сложностей. В этом примере: Основной скрипт (main.lua) работает в бесконечном цикле. Он проверяет, запущен ли другой скрипт (other_script.lua), с помощью функции check_if_other_script_running. Если другой скрипт не запущен, он запускает его с помощью dofile("other_script.lua"). После завершения работы другого скрипта, флаг is_other_script_running сбрасывается.

Вы поднимаете более сложный вопрос, о взаимодействии между скриптами в окружении терминала, в контексте Lua. И отвечаете, прямое управление скриптами в терминале невозможно, но есть обходные пути.
 
Цитата
Saturn написал:
Возможно ли с помощью одного скрипта запустить другой ?
Полагаю, что вопрос не о запуске lua функций из файлов, а именно скриптов QUIK на основе библиотеки QLua так как это две большие разницы.
------------------------  
Запуск функций  из файлов с помощью dofile  в вызывающем их потоке.
Т е сколько бы функций не запустили будет основной поток с колбеками и поток main.
-------------------------
При запуске скриптов QUIK  будет создаваться новый поток main.
Таким способом можно запустить столько потоков сколько хочется.
------------------------------
Сделать это можно.  
 
но сложнее, чем просто запуск из файлов.
 
Ну вы конечно очень глубоко копнули, а человек спросил просто можно ли одним скриптом в окне "доступные скрипты" перевести второй скрипт из состояния "остановлен" в состояние "запущен".

Штатными средствами сделать этого нельзя.
Понятно что имея возможность запускать любой код в подключаемых библиотеках можно сделать вообще все что угодно, однако это не будет хорошим решением.
 
Цитата
Станислав написал:
Ну вы конечно очень глубоко копнули, а человек спросил просто можно ли одним скриптом в окне "доступные скрипты" перевести второй скрипт из состояния "остановлен" в состояние "запущен".

Штатными средствами сделать этого нельзя.
Понятно что имея возможность запускать любой код в подключаемых библиотеках можно сделать  вообще все что угодно , однако это не будет хорошим решением.
Задача решается с помощью механизма Event (ранее об этом говорил как альтернатива использования sleep в main).  
 
И еще...
Нет смысла запускать скрипты с помощью dofile (особенно как в приведенном VPM примере)
Так как это лишь замедляет исполнение.
---------------
dofile имеет смысл применять для разделения большого скрипта на блоки,
чтобы упростить чтение и отладку скрипта.
 
Цитата
nikolz написал:
И еще...Нет смысла запускать скрипты с помощью dofile (особенно как в приведенном VPM примере)Так как это лишь замедляет исполнение.---------------dofile имеет смысл применять для разделения большого скрипта на блоки, чтобы упростить чтение и отладку скрипта.
nikolz, Пример выше это просто демонстрация возможностей, ни на что не претендующая.
К примеру у себя использую следующий вариант (кусочек из рабочего код):  
Код
-- Пытаемся загрузить библиотеку
            local fuzzy;
            local success, err = pcall(dofile, path..'\\luafuzzy.lua')
            if not success then
                Log:error("Ошибка при загрузке файла luafuzzy: " .. err)
            else
                -- Если библиотека успешно загружена, используем её
                local fuzzy = luafuzzy()
                Log:info("Библиотека luafuzzy успешно загружена!")
            end

    while WORKING_FLAG do
Перед основным циклом while WORKING_FLAG do 1 раз вызываем "Пан или пропал!" :smile: , ни чего не замедляем, просто Функция dofile выполнит Lua-скрипт, и все переменные и функции, определённые в нём, будут доступны в текущем окружении. И смысл здесь в подключении новой задачи!
 
Цитата
VPM написал:
Цитата
nikolz написал:
И еще...Нет смысла запускать скрипты с помощью dofile (особенно как в приведенном VPM примере)Так как это лишь замедляет исполнение.---------------dofile имеет смысл применять для разделения большого скрипта на блоки, чтобы упростить чтение и отладку скрипта.
nikolz, Пример выше это просто демонстрация возможностей, ни на что не претендующая.
К примеру у себя использую следующий вариант (кусочек из рабочего код):  
Код
   -- Пытаемся загрузить библиотеку 
             local  fuzzy;
             local  success, err  =  pcall(dofile, path .. '\\luafuzzy.lua')
             if   not  success  then 
                Log:error( "Ошибка при загрузке файла luafuzzy: "   ..  err)
             else 
                 -- Если библиотека успешно загружена, используем её 
                 local  fuzzy  =  luafuzzy()
                Log:info( "Библиотека luafuzzy успешно загружена!" )
             end 

     while  WORKING_FLAG  do   
Перед основным циклом while WORKING_FLAG do 1 раз вызываем "Пан или пропал!" :: , ни чего не замедляем, просто Функция dofile выполнит Lua-скрипт, и все переменные и функции, определённые в нём, будут доступны в текущем окружении. И смысл здесь в подключении новой задачи!
Вообще-то загрузка библиотеки и запуск скрипта в вашем примере это две большие разницы.
Поясняю.
Загрузка библиотек делается как правило один раз при запуске скрипта. Это необходимая операция, так как библиотек много разных  и разумно не изобретать велосипед, а использовать готовый.
Так как загрузка изначально и однократно, то не имеет значение время загрузки.
-----------------------  
В вашем примере Вы грузите и запускаете скрипт не однократно, так как используете флаг загрузки.
Но нет смысла грузить и запускать скрипт  т. е. многократно его грузить.
Я через dofile загружаю свои библиотеки функций с целью разделить большой скрипт на части и отлаживать эти части отдельно. Фактически это вариант создания библиотеки, с упрощением обмена данными через глобальный стек.  
 
nikolz, Да Вы совершено правы, я лишь хотел подчеркнуть особенность подключения
Цитата
VPM написал:
Функция dofile выполнит Lua-скрипт, и все переменные и функции, определённые в нём, будут доступны в текущем окружении. И смысл здесь в подключении новой задачи!
Ведь есть еще способ  local Utility = require("Utility").
 
Цитата
VPM написал:
nikolz, Да Вы совершено правы, я лишь хотел подчеркнуть особенность подключения  
Цитата
VPM написал:
Функция dofile выполнит Lua-скрипт, и все переменные и функции, определённые в нём, будут доступны в текущем окружении. И смысл здесь в подключении новой задачи!
Ведь есть еще способ  local Utility = require("Utility").
require  - это способ подключения готовых (не собственных) библиотек в том числе на С.  Но при этом вы не можете передать в из них данные через глобальный стек.
-------------------
Повторю свое мнение. dofile -не для подключения новой задачи, а для разделения длинного скрипта на отдельные куски, чтобы было проще читать и отлаживать.  
---------------------
Аналогия на книжках примерно такая:
подключение библиотек с помощью   require  - это как сборка коллекции различных книг.
а применение dofile - это как сборка книжки их листов.  
Страницы: 1
Читают тему
Наверх