nikolz (Все сообщения пользователя)

Выбрать дату в календареВыбрать дату в календаре

Страницы: Пред. 1 ... 10 11 12 13 14 15 16 17 18 19 20 ... 80 След.
Очередь -элементарно и полезно, Как сделать очередь в роботе и зачем.
 
Примечательно то, что наличие очереди дает нам возможность получить и обработать все события, которые принимают колбеки вне зависимости от величины времени  бездействия  функции sleep.
----------------
Если бы я не использовал очередь, то в случае sleep(1000) - 1 секунда, в каждом цикле терялись несколько десятков событий.
Если посмотрите тему "мой робот", то там видно что за 5 секунд приходит до 3000 событий, которые без организации очереди просто потеряются.
=====================
А теперь я объясню как в моем скрипте организована очередь и почему она такая простая.
---------------
Очередь реализована так.
строка:
Код
_N=0; _tN={};
в ней задается счетчик элементов очереди _N
и таблица для этих элементов
-------------------
запись элемента в очередь производится в колбеках всегда одинаково просто:
Код
  _N=_N+1; _tN[_N]={1,t}; 
а для колбека onParam так:
Код
 _N=_N+1; _tN[_N]={99,c,s,tim};

т е увеличиваем счетчик элементов
и записываем в таблицу по значению счетчика   ключ и передаваемые параметры.
-----------------------
При записи не требуется никакой синхронизации, так как запись лишь в колбеках, а они в одном потоке.
----------------------
Чтение и удаление элемента из очереди реализована в функции main  так:
Код
   t=_tN[_N]; _N=_N-1 

Элемент не удаляется, а уменьшается лишь счетчик.
Удаление элемента произойдет лишь, если на его место будет записан новый элемент в колбеке.
=====================
Вот и вся очередь.
-----------------------
Все просто , но весьма эффективно.
---------------------
Далее я расскажу как сделать обработку еще быстрее, но не сложнее.
-----------------
Продолжение возможно следует..  
Очередь -элементарно и полезно, Как сделать очередь в роботе и зачем.
 
В данном варианте скрипта у нас нет информации о времени исполнения каких-либо фрагментов.
изменим скрипт и добавим измерения времени исполнения.
кроме того, начнем процесс изучения с классической рекомендации разработчиков - поставить sleep на 1 секунду
вот такой скрипт:
Код
name="bot";  -- имя робота
path = "D:/QUIK_SCRIPT/nk_bot/"   --папка где разместим лог файл
Log=io.open(path..name..".log","w")   -- создаем лог файл для записи
------------
_N=0; _tN={};
----------------------
function main()
-----------------------
   while fconnect do
      if getInfoParam("SERVERTIME") then
         DT=getInfoParam("TRADEDATE"); DT=tonumber(string.sub (DT,7,10)..string.sub (DT,4,5)..string.sub (DT,1,2));
         fconnect=2;
         Log:write("DT="..tostring(DT)..",fconnect="..fconnect.."\n");Log:flush();
      end
------------------------------

      local clas,sec,ncb,t,_time,tim1,tim2,T;
      local tim0,tim1,tim2,T;
-----------------------------
      while fconnect==2 do
         while _N>0 do
            t=_tN[_N]; _N=_N-1  ncb=t[1];
   ----------------------
            if ncb==99 then
               clas,sec=t[2],t[3]; tim1=t[4];

            else
               t=t[2];
               if ncb==1 then
                  clas=t.class_code; sec=t.sec_code; --может не быть
               elseif ncb==2 then
                  clas=t.class_code; sec=t.sec_code;
               end
            end
            T=os.sysdate(); tim=60.*(60.*T.hour+T.min)+T.sec+0.001*(T.ms+0.001*T.mcs);
            tim=(1000000.*(tim-tim1))//1;
            Log:write(ncb..",tim="..tim..",clas="..tostring(clas)..",sec="..tostring(sec)..",_N=".._N.."\n");Log:flush();
         end
            sleep(1000);
      end
   end
end
----------------------------
function OnInit(pfile)    fconnect=isConnected(); end
----------------
function OnParam(c,s)
local T=os.sysdate(); local tim=60.*(60.*T.hour+T.min)+T.sec+0.001*(T.ms+0.001*T.mcs)
      _N=_N+1; _tN[_N]={99,c,s,tim};
end
function OnTransReply(t)        _N=_N+1; _tN[_N]={1,t}; end
function OnOrder(t)            _N=_N+1; _tN[_N]={2,t}; end
это результат в лог файле:
Код
DT=20240119,fconnect=2
99,tim=218014.0,clas=SPBFUT,sec=EuH4,_N=25
99,tim=304359.0,clas=SPBFUT,sec=SVH4,_N=24
99,tim=541966.0,clas=SPBFUT,sec=NKH4,_N=23
99,tim=595608.0,clas=CETS,sec=EUR_RUB__TOD,_N=22
99,tim=1213820.0,clas=SPBFUT,sec=EuH4,_N=21
99,tim=1344144.0,clas=SPBFUT,sec=GZH4,_N=20
99,tim=1404051.0,clas=SPBFUT,sec=EuH4,_N=19
99,tim=587619.0,clas=CETS,sec=EUR_RUB__TOD,_N=18
99,tim=587619.0,clas=SPBFUT,sec=EDH4,_N=17
99,tim=772196.0,clas=QJSIM,sec=YNDX,_N=16
99,tim=772196.0,clas=QJSIM,sec=WUSH,_N=15
99,tim=772196.0,clas=QJSIM,sec=TGKA,_N=14
99,tim=772196.0,clas=QJSIM,sec=TATNP,_N=13
99,tim=772196.0,clas=QJSIM,sec=SNGS,_N=12
99,tim=772196.0,clas=QJSIM,sec=SFIN,_N=11
99,tim=772196.0,clas=QJSIM,sec=SBER,_N=10
99,tim=772196.0,clas=QJSIM,sec=RTKMP,_N=9
99,tim=772196.0,clas=QJSIM,sec=RTKM,_N=8
99,tim=772196.0,clas=QJSIM,sec=OZON,_N=7
99,tim=772196.0,clas=QJSIM,sec=MTLR,_N=6
99,tim=772196.0,clas=QJSIM,sec=KGKCP,_N=5
99,tim=772196.0,clas=QJSIM,sec=IRAO,_N=4
99,tim=772196.0,clas=QJSIM,sec=GLTR,_N=3
99,tim=772196.0,clas=QJSIM,sec=GAZP,_N=2
99,tim=772196.0,clas=QJSIM,sec=ALRS,_N=1
99,tim=772196.0,clas=QJSIM,sec=ABIO,_N=0
99,tim=61608.0,clas=SPBFUT,sec=EuH4,_N=26
99,tim=127575.0,clas=SPBFUT,sec=BRH4,_N=25
99,tim=559817.0,clas=CETS,sec=EURUSD000TOD,_N=24
99,tim=653453.0,clas=SPBFUT,sec=EuH4,_N=23
99,tim=899874.0,clas=SPBFUT,sec=CRH4,_N=22
99,tim=995760.0,clas=SPBFUT,sec=GZH4,_N=21
99,tim=1022059.0,clas=QJSIM,sec=WUSH,_N=20
99,tim=1022059.0,clas=QJSIM,sec=TTLK,_N=19
99,tim=1022059.0,clas=QJSIM,sec=TGKA,_N=18
99,tim=1022059.0,clas=QJSIM,sec=TCSG,_N=17
99,tim=1022059.0,clas=QJSIM,sec=SOFL,_N=16
99,tim=1022059.0,clas=QJSIM,sec=SFIN,_N=15
99,tim=1022059.0,clas=QJSIM,sec=SBERP,_N=14
99,tim=1022059.0,clas=QJSIM,sec=SBER,_N=13
99,tim=1022059.0,clas=QJSIM,sec=RTKM,_N=12
99,tim=1022059.0,clas=QJSIM,sec=MTSS,_N=11
99,tim=1022059.0,clas=QJSIM,sec=MTLR,_N=10
99,tim=1022059.0,clas=QJSIM,sec=KZOSP,_N=9
99,tim=1022059.0,clas=QJSIM,sec=KGKCP,_N=8
99,tim=1022059.0,clas=QJSIM,sec=IRAO,_N=7
99,tim=1022059.0,clas=QJSIM,sec=GAZP,_N=6
99,tim=1022059.0,clas=QJSIM,sec=ALRS,_N=5
99,tim=1430033.0,clas=SPBFUT,sec=SiH4,_N=4
99,tim=619443.0,clas=CETS,sec=SLVRUB_TOM,_N=3
99,tim=619443.0,clas=SPBFUT,sec=EuH4,_N=2
99,tim=681738.0,clas=SPBFUT,sec=EuH4,_N=1
99,tim=805853.0,clas=SPBFUT,sec=SGH4,_N=0
99,tim=311503.0,clas=QJSIM,sec=WUSH,_N=23
99,tim=311503.0,clas=QJSIM,sec=SNGS,_N=22
99,tim=311503.0,clas=QJSIM,sec=SFIN,_N=21
99,tim=311503.0,clas=QJSIM,sec=SBERP,_N=20
В лог файле есть два значения времени tim, - задержка исполнения колбека onParam в main
Как видно из лог файла , Как видим из лог файла очередь на обработку никогда не бывает пустой.
Задержка составляет от 0.3 до 0.8 сек. В лог файле она в мкс.
--------------------------
функция sleep установлена чтобы уменьшить загрузку ядра процессора холостыми циклами.
Поэтому посмотрим в диспетчере задач эту загрузку.
Она составляет:


Примерно 8.5%
теперь давайте уменьшим эту величину до 1 ms
в результате получим:
Код
DT=20240119,fconnect=2
99,tim=32006.0,clas=SPBFUT,sec=SiH4,_N=1
99,tim=32006.0,clas=SPBFUT,sec=SiH4,_N=0
99,tim=31589.0,clas=SPBFUT,sec=RNH4,_N=1
99,tim=31589.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=24404.0,clas=SPBFUT,sec=SiH4,_N=2
99,tim=24404.0,clas=SPBFUT,sec=SPH4,_N=1
99,tim=24404.0,clas=SPBFUT,sec=EuH4,_N=0
99,tim=32006.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=30568.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=30675.0,clas=SPBFUT,sec=RNH4,_N=2
99,tim=30675.0,clas=SPBFUT,sec=SPH4,_N=1
99,tim=30675.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=30164.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=20010.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=30185.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=28578.0,clas=SPBFUT,sec=RIH4,_N=1
99,tim=28578.0,clas=SPBFUT,sec=SiH4,_N=0
99,tim=4000.0,clas=SPBFUT,sec=EuH4,_N=0
99,tim=26515.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=2383.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=30316.0,clas=SPBFUT,sec=SiH4,_N=1
99,tim=30316.0,clas=SPBFUT,sec=SiH4,_N=0
99,tim=31911.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=11245.0,clas=SPBFUT,sec=VBH4,_N=2
99,tim=11245.0,clas=SPBFUT,sec=VBH4,_N=1
99,tim=11508.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=11998.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=28664.0,clas=SPBFUT,sec=SiH4,_N=0
99,tim=27900.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=831.0,clas=SPBFUT,sec=BRG4,_N=0
99,tim=11832.0,clas=SPBFUT,sec=GZH4,_N=1
99,tim=11832.0,clas=SPBFUT,sec=EuH4,_N=0
99,tim=11998.0,clas=CETS,sec=TRYRUB_TOM,_N=1
99,tim=11998.0,clas=CETS,sec=CNYRUB_TOM,_N=0
99,tim=31687.0,clas=SPBFUT,sec=GZH4,_N=0
99,tim=23877.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=11997.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=31793.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=30233.0,clas=SPBFUT,sec=SPH4,_N=0
99,tim=29818.0,clas=SPBFUT,sec=MMH4,_N=0
99,tim=30141.0,clas=SPBFUT,sec=RNH4,_N=0
99,tim=1998.0,clas=QJSIM,sec=YNDX,_N=19
99,tim=1998.0,clas=QJSIM,sec=WUSH,_N=18
99,tim=1998.0,clas=QJSIM,sec=VTBR,_N=17
99,tim=1998.0,clas=QJSIM,sec=VKCO,_N=16
99,tim=1998.0,clas=QJSIM,sec=TCSG,_N=15
99,tim=1998.0,clas=QJSIM,sec=SFIN,_N=14
99,tim=1998.0,clas=QJSIM,sec=SELG,_N=13
99,tim=1998.0,clas=QJSIM,sec=SBER,_N=12
99,tim=1998.0,clas=QJSIM,sec=ROSN,_N=11
99,tim=1998.0,clas=QJSIM,sec=OZON,_N=10
99,tim=1998.0,clas=QJSIM,sec=MOEX,_N=9
99,tim=1998.0,clas=QJSIM,sec=LKOH,_N=8
99,tim=1998.0,clas=QJSIM,sec=KAZTP,_N=7
99,tim=1998.0,clas=QJSIM,sec=IRAO,_N=6
99,tim=4000.0,clas=QJSIM,sec=GLTR,_N=5

Задержка составляет 1998 мкс примерно 2 ms.  Очередь бывает пустой.
Смотрим загрузку ядра:

Примерно 10%. Что вполне допустимо
------------------
Продолжение следует...
Очередь -элементарно и полезно, Как сделать очередь в роботе и зачем.
 
Тем, кто хотел бы практически разобраться в данном вопросе, рекомендую установить демо КВИК
и запускать скрипты, которые я буду выкладывать и пояснять.
Итак начнем.
Вот исходный скрипт, в нем закомментированы некоторые операторы, которые демонстрируют однотипность записи колбеков
и их обработку в функции main.
В первых трех строчках скрипта создаемся лог файл, куда скрипт выводит информацию о своей работе.
Вам надо исправить 2-ю строку, записав в ней путь, где Вы хотите создать этот файл
Код
name="bot";  -- имя робота
path = "D:/QUIK_SCRIPT/nk_bot/"   --папка где разместим лог файл
Log=io.open(path..name..".log","w")   -- создаем лог файл для записи
------------
_N=0; _tN={};
----------------------
function main()
-----------------------
   while fconnect do
      if getInfoParam("SERVERTIME") then
         DT=getInfoParam("TRADEDATE"); DT=tonumber(string.sub (DT,7,10)..string.sub (DT,4,5)..string.sub (DT,1,2));
         fconnect=2;
         Log:write("DT="..tostring(DT)..",fconnect="..fconnect.."\n");Log:flush();
      end
------------------------------

      local clas,sec,ncb,t,_time;
-----------------------------
      while fconnect==2 do
         while _N>0 do
            t=_tN[_N]; _N=_N-1  ncb=t[1];
   ----------------------
            if ncb==99 then
               clas,sec=t[2],t[3];
            else
               t=t[2];
               if ncb==1 then
                  clas=t.class_code; sec=t.sec_code; --может не быть
               elseif ncb==2 then
                  clas=t.class_code; sec=t.sec_code;
--               elseif ncb==3 then
--               elseif ncb==4 then
--               elseif ncb==5 then
--               elseif ncb==6 then
--               elseif ncb==7 then
--               elseif ncb==8 then
--               elseif ncb==9 then
--               elseif ncb==10 then
--               elseif ncb==11 then
--               elseif ncb==12 then
               end
            end
            Log:write(ncb..",clas="..tostring(clas)..",sec="..tostring(sec)..",_N=".._N.."\n");Log:flush();
            _time=0;
         end
         sleep(1);
      end
   end
end
----------------------------
function OnInit(pfile)    fconnect=isConnected(); end
----------------
function OnParam(c,s)                _N=_N+1; _tN[_N]={99,c,s,tim};end
---------------------
function OnTransReply(t)        _N=_N+1; _tN[_N]={1,t}; end
function OnOrder(t)            _N=_N+1; _tN[_N]={2,t}; end
--function OnStopOrder(t)       _N=_N+1; _tN[_N]={3,t}; end
--function OnTrade(t)              _N=_N+1; _tN[_N]={4,t}; end
--function OnQuote(c,s)           _N=_N+1; _tN[_N]={5,t}; end
--function OnAllTrade(t)       _N=_N+1; _tN[_N]={6,t}; end
--function OnDepoLimit(t)         _N=_N+1; _tN[_N]={7,t}; end
--function OnAccountBalance(t)             _N=_N+1; _tN[_N]={8,t}; end-- изменение позиции по счету
--function OnAccountPosition(t)    _N=_N+1; _tN[_N]={9,t}; end-- изменение позиции по счету
--function OnDepoLimit(t)       _N=_N+1; _tN[_N]={10,t}; end -- изменение позиции по инструментам
--function OnFuturesClientHolding(t) _N=_N+1; _tN[_N]={11,t}; end  -- изменение позиции по срочному рынку
--function OnMoneyLimit(t)       _N=_N+1; _tN[_N]={12,t}; end -- изменение денежной позиции

--function OnClose() fconnect=nil end
--function OnConnected(flag) fconnect=1; end
--function OnDisconnected() fconnect=1 end
--function OnStop(flag) fconnect=nil; return 2000 end
--function OnCleanUp()  end -- смена торговой сессии
--function OnDepoLimitDelete(t) end -- удаление позиции по инструментам
--function OnFirm(t) end -- получение описания новой фирмы
--function OnFuturesLimitChange(t) end -- изменение ограничений по срочному рынку
--function OnFuturesLimitDelete(t) end -- удаление лимита по срочному рынку
--function OnMoneyLimitDelete(t) end -- удаление денежной позиции
--function OnNegDeal end-- новая заявка на внебиржевую сделку или изменение параметров существующей заявки на внебиржевую сделку
--function OnNegTrade end-- новая сделка для исполнения или изменение существующей сделки для исполнения
для наглядности уберем эти комментарии:
Код
name="bot";  -- имя робота
path = "D:/QUIK_SCRIPT/nk_bot/"   --папка где разместим лог файл
Log=io.open(path..name..".log","w")   -- создаем лог файл для записи
------------
_N=0; _tN={};
----------------------
function main()
-----------------------
   while fconnect do
      if getInfoParam("SERVERTIME") then
         DT=getInfoParam("TRADEDATE"); DT=tonumber(string.sub (DT,7,10)..string.sub (DT,4,5)..string.sub (DT,1,2));
         fconnect=2;
         Log:write("DT="..tostring(DT)..",fconnect="..fconnect.."\n");Log:flush();
      end
------------------------------

      local clas,sec,ncb,t,_time;
-----------------------------
      while fconnect==2 do
         while _N>0 do
            t=_tN[_N]; _N=_N-1  ncb=t[1];
   ----------------------
            if ncb==99 then
               clas,sec=t[2],t[3];
            else
               t=t[2];
               if ncb==1 then
                  clas=t.class_code; sec=t.sec_code; --может не быть
               elseif ncb==2 then
                  clas=t.class_code; sec=t.sec_code;
               end
            end
            Log:write(ncb..",clas="..tostring(clas)..",sec="..tostring(sec)..",_N=".._N.."\n");Log:flush();
            _time=0;
         end
         sleep(1);
      end
   end
end
----------------------------
function OnInit(pfile)    fconnect=isConnected(); end
----------------
function OnParam(c,s)        _N=_N+1; _tN[_N]={99,c,s,tim};end
---------------------
function OnTransReply(t)        _N=_N+1; _tN[_N]={1,t}; end
function OnOrder(t)            _N=_N+1; _tN[_N]={2,t}; end
Запустим этот скрипт на исполнение
и получим следующий результат в лог файле
Код
DT=20240119,fconnect=2
99,clas=SPBFUT,sec=SiH4,_N=0
99,clas=SPBFUT,sec=MMH4,_N=0
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=SFH4,_N=0
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=EuH4,_N=1
99,clas=SPBFUT,sec=USDRUBF,_N=0
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=USDRUBF,_N=0
99,clas=CETS,sec=USDCNY_TOM,_N=4
99,clas=CETS,sec=EURUSD000TOD,_N=3
99,clas=CETS,sec=CNYRUB_TOM,_N=2
99,clas=CETS,sec=EUR_RUB__TOM,_N=1
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=TNH4,_N=1
99,clas=SPBFUT,sec=EuH4,_N=0
99,clas=SPBFUT,sec=SGH4,_N=0
99,clas=SPBFUT,sec=CHH4,_N=0
99,clas=SPBFUT,sec=SGH4,_N=1
99,clas=SPBFUT,sec=CHH4,_N=0
99,clas=SPBFUT,sec=LKH4,_N=1
99,clas=SPBFUT,sec=SGH4,_N=0
99,clas=SPBFUT,sec=TNH4,_N=3
99,clas=SPBFUT,sec=TNH4,_N=2
99,clas=SPBFUT,sec=EDH4,_N=1
99,clas=SPBFUT,sec=EDH4,_N=0
99,clas=QJSIM,sec=WUSH,_N=12
99,clas=QJSIM,sec=UPRO,_N=11
99,clas=QJSIM,sec=UGLD,_N=10
99,clas=QJSIM,sec=SIBN,_N=9
99,clas=QJSIM,sec=NMTP,_N=8
99,clas=QJSIM,sec=MTLR,_N=7
99,clas=QJSIM,sec=MDMG,_N=6
99,clas=QJSIM,sec=GLTR,_N=5
99,clas=QJSIM,sec=CHMF,_N=4
99,clas=QJSIM,sec=ALRS,_N=3
99,clas=QJSIM,sec=ABIO,_N=2
99,clas=SPBFUT,sec=CRH4,_N=1
99,clas=SPBFUT,sec=TNH4,_N=0

Последним значением в строке переменная _N - длина очереди.
--------------
Пояснение следует...
Очередь -элементарно и полезно, Как сделать очередь в роботе и зачем.
 
Добрый день,
Хочу поделиться некоторыми приемами, которые я использую при построении своих роботов.
См. тему -мой робот.
-----------------
В структуре спинного мозга робота , реализуемого в QUIK, условно можно выделить колбеки,
в которые приходят сообщения о событиях и функцию main,
работающую в отдельном потоке, которая обрабатывает эти события.
-------------------
Как правило, в  main делается бесконечный цикл, в котором и осуществляется обработка.
------------------------
Если обрабатывать нечего, то рекомендуют ставить sleep(time) , где time - число миллисекундах,
на которое Вы заморозите работу main.
===============
Но проблема в том, что пока Main не работает, в колбеки поступают события ,
которые надо обрабатывать либо как-то сохранить иначе они потеряются.
------------------------------
Если обрабатывать события  в колбеках, то на время обработки будет остановлен терминал QUIK, так как колбеки работают в основном потоке термина.
------------------
Проблема решается путем сохранения сообщений из колбеков в массиве,
из которого потом main сможет обработать все сохраненные сообщения.
Такой список (массив,таблица и т д) сообщений называется очередью.
===================
Вопрос лишь в том, как организовать эту очередь , чтобы было просто и быстро.
---------------
Есть несколько вариантов,
------------
Вариант 1: классический - это сделать универсальные списки, очереди. Алгоритмов и их реализаций много можно найти в интернете.
Сложно, малопонятно не спецам . Большая нагрузка на сборщик мусора, что замедляет исполнение скрипта.
--------------------
Вариант 2: -рекомендуемый  в документации QLUA - использовать потоко безопасные функции записи и удаления из массива.
Просто, но относительно медленно.
-------------------
Вариант 3:   это мой, тот который я расскажу далее. просто и быстро.
Объяснять буду на рабочем примере.
-------------------
Продолжение следует...

 
Lua таблицу в файл и обратно
 
еще вариант преобразования таблицы в скрипт Lua
Код
function t2s(t,s) -- преобразование таблицы в скрипт Lua
   for z,v in pairs(t) do
   if s~="" then s=s.."," end
       if type(z)~="number" then s=s.."["..z.."]=" end
      m=type(v);
      if m=="table" then x=t2s(v,"")
        elseif m=="number" then  x=v;
      else x='"'..v..'"';   end
      s=s..x;
    end
return "{"..s.."}";
end
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
а теперь хвалюсь. На сегодня 5.98%. Подробности на картинке.

Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Выложенный скрипт  очереди Владимира - это просто ужас какой-то.
Сборщик мусора сойдет с ума.
Берем такой  два варианта :
Код
--сравнительный тест размер массива
local M=1000000
local list=List.new()
local tnk=nkcc.new(32);
nklib.startA();  for i=1, M do push(tnk,i); end  tim1=nklib.stopA();
print("замер массива после"..M.." циклов push="..#tnk)
nklib.startA();  for i=1, M do local x=pop(tnk); end  tim2=nklib.stopA();
print("замер массива после"..M.." циклов pop="..#tnk)
nklib.startA();  for i=1, M do local x=get(tnk,i); end  tim3=nklib.stopA();
print("замер массива после"..M.." циклов pop="..#tnk)
print(tim0,tim01,tim1,tim2,tim3,tim0/tim1,tim01/tim2,tim01/tim3);

а это результат:
Код
>D:/lua53/lua53.exe -e "io.stdout:setvbuf 'no'" "Test_List.lua" 
замер массива после1000000 циклов push=999999
замер массива после1000000 циклов pop=0
739889   798541
замер массива после1000000 циклов push=33
замер массива после1000000 циклов pop=33
замер массива после1000000 циклов pop=33
739889   798541   668524   665355   742990   1.1067500942375   1.2001728400628   1.0747668205494
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата
VPM написал:
Цитата
Glukator написал:
Да хрен его знает, этого прохвоссора, о чем он толкует. У вас какое-то конкретное практическое приложение намечено для этих структур?

Да уж куда еще конкретней. Попробую сформировать свою Задачу.

Эта тема лежит в начале обсуждения (пост #1) на этой веточки. Но куда то подевались программисты? Все "понты" по отлетали. Лучше месяцами "толочь воду в ступе" про OnInit и тому подобное.
Это делается организацией циклическим массивом.
Например, в индикаторах используем не более 32 отсчетом .
это тест в нем внешний цикл это поступающие отсчеты
А внутренний цикла печатает какие отсчеты сейчас внутри массива
Код
local M=1000000
local tnk=newV(32);
 for i=1, M do push(tnk,i);
local t1={}
for i=1,32 do t1[i]=get(tnk,i); end
print(table.concat(t1,","));
end
и вот результат: Массив содержит всегда последние 32 элемента . Сборщик мусора отдыхает.
Могу показать как работает стек с фиксированной длинной и очередь с циклическим массивом.
А ту очередь, которую Вам гуру по прогаммированию написалчто Вам раноше
Код
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17
0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18
0,0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19
0,0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20
0,0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21
0,0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22
0,0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23
0,0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24
0,0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25
0,0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26
0,0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27
0,0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28
0,0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29
0,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30
0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31
1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32
2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33
3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34
4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35
5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36
6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37
7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38
8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39
9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40
10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41
11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42
12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43
13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44
14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45
15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46
16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47
17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48
18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49
19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50
20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51
21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52
22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53
23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54
24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55
25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56
26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57
27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58
28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59
29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60
30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61
31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62
32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63
33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64
34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65
35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66
36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67
37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68
38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69
39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70
40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71
41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72
42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73
43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74
44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75
45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76
46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77
47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78
48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79
49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80
50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81
51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82
52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83
53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84
54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85
55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86
56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87
57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88
58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89
59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90
60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91
61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92
62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93
63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94
64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95
65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96
66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97
67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98
68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99
69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100
70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101
71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102
72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103
73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104
74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105
75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106
76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107
77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108
78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109
79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110
80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111
81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112
82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113
83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114
84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115
85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116
86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117
87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118
88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119
89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120
90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121
91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122
92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123
93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124
94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125
95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126
96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127
97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128
98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129
99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130
100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131
101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132
102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133
103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134
104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135
105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136
106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137
107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138
108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139
109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140
110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141
111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142
112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143
113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144
114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145
115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146
116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147
117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148
118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149
119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150
66,167,168,169,170
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата

List.pushlast: ; number; ; list.last=0; number; list[last]=40
тут ошибки
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
VPM,
В качестве информации к размышлению.
---------------------
Вы наверное видели на форуме результаты теста хранения и обмена данных по принципу Memory-mapped files
-------------------  
Так вот , применение отображения файла на память решает все проблемы с объемом памяти.
----------------------------------------
1)  Объем памяти для хранения данных.
У меня он ограничен свободным объемом диска. сейчас это 100 ГБайт.
Очевидно, что если мало, то можно добавить еще диск специально для данных, например 500 Гбайт
Цена вопроса 2тр.  Понятно, что объем памяти для хранения данных практически любой.
---------------------------------------
2) Объем памяти для обработки данных.
Очевидно, что обрабатывать  500 Гбайт каждую минуту нет надобности.  
У меня на компе есть сейчас  свободных  2.5Гбайта .
Для обработки за один заход  мне достаточно 1 ГБайт.
------------------------------------
3) Фокус в том, что на этот 1Гбайт  менее, чем за 0.001 сек проецирую  любой ГБайт из файла на диске.
После проецирования работа с Гбайтом данных выполняется в памяти.
----------------
Более того, не надо ничего читать из файлов в другие потоки или приложения.
------------------------
Они видят эту оперативную память и просто работают с ней как обычно.
=========================
Резюме, нет никаких ограничений ни в памяти для обработки , ни в памяти для хранения.
 
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Хвалюсь:
Lua таблицу в файл и обратно
 
Serge123,
За базар отвечаешь?
-------------------
Разуй глаза:
Lua таблицу в файл и обратно
 
Цитата
Serge123 написал:
bot4sale.ru/blog-menu/qlua/300-table-tostring.html
Можешь доказать?
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
VPM,
Вы рыбак?  Покупали лодку на Аральском море ?
-----------------
Если нет, то Ваш пример из раздела - " Остапа понесло"  
---------------  
Всегда прикольно, когда начинают рассказывать примеры из совершенно чужой области деятельности.
===========
Типа:  "А вот им это очень нужно"
или "в будущем это особо пригодится тем, .... "
и так далее...
Cкорость обмена данными через файлы
 
Цитата
Serge123 написал:
А если диск виртуальный, то как по сравнению с маппинг филес?
У меня нет виртуального диска.
Могу предположить что разницы в скорости нет так как обмен практически через память ,
но в маппинге параллельно получаем файл в энергонезависимой памяти (диске). и нет надобности тратить память на виртуальный диск.
Ну и безусловно, если данных  сотни гигабайт или терабайты, то никакой виртуальный диск  не поможет.
------------------------------
Возможно обмен через Shared Memory будет быстрее.  
Cкорость обмена данными через файлы
 
сделал тест обмена данными приложения Lua и  Python.
--------------------
для mapping falles скорость обмена 21 МБ/сек.
Просто файлами  0.8 МБ/сек.
Аналогично между приложениями на Lua.
------------------
Функции обмена реализованы на С.
Ограничения при использовании QuikSharp.lua
 
Цитата
bespalex написал:
Цитата
nikolz написал:
Я выкладывал тесты.
Но с питоном не делал.
Он медленнее luajit примерно в 30 раз.
да уже увидел тесты
сделал тест обмена данными приложения Lua и  Python.
--------------------
для mapping falles скорость обмена 21 МБ/сек.
Просто файлами  0.8 МБ/сек.
Аналогично между приложениями на Lua.
------------------
Функции обмена реализованы на С.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Продолжаю хвалится.
--------------------------
Те кому рябит, смотрите только нижнюю картинку
это профит - рассчитывается с начала этого года (есть за 2023 и частично за 2022)
--------------
белая линия - это суммарный профит
зеленая линия - это лонг
синяя - это шорт
штриховые линии - это текущий расчет.
=================
Графики использую для обучения.
Этот робот реализует NN -"обучение с учителем"
-----------------
С самообучением пока лишь стою.
==============
На верхнем графики автоматически строятся уровни поддержки и сопротивления и линии регрессии.  
Ограничения при использовании QuikSharp.lua
 
Я выкладывал тесты.
Но с питоном не делал.
Он медленнее luajit примерно в 30 раз.
Ограничения при использовании QuikSharp.lua
 
Цитата
bespalex написал:
Цитата
nikolz написал:
 
Цитата
bespalex  написал:
   перебор тоже вариант  
Чаще всего отключение происходит ровно в 10:00:05. Не знаю, может какое-то технологическое переключение в начале сессии, которое триггерит выкидыш. Не думаю, что если бы дело было в core.dll оно бы так выглядело.
  Дело в том, что нет смысла передавать все данные из КВИК через луа в питон.
-------------
Моя концепция создания робота такая:
-----------
Робот условно содержит две части - я их назвал по аналогии с человеком - спинной и головной мозг.
Спинной - это все колбеки в КВИКЕ и все торговые операции в КВИКЕ.
Их нет смысла  перегонять в питон и обратно.
Это фактически автомат стандартных действий, которые не зависят никак от стратегии и тактики торговли.
Эту часть я реализую в КВИКЕ на луа + си for lua.
------------------
Головной мозг -  это прогнозы, управление капиталом, стратегии торговли можно и нужно реализовывать
в дополнительных потоках и приложениях  на любых языках, в том числе и питоне.
---------------------  
Вот для этого организую  взаимодействие КВИКа через Луа с python, rust,julia, terra, luajit и т д
================  
Сейчас обмен любыми данными делаю через mapping files.
Скорость обмена просто аховая, так как это обмен через память .
Нет никаких оберток. Поддерживаются все форматы.
Строки передаю как хеш.  Это фактически два целых числа.
Объем данных ограничен лишь объемом дисков.
----------------------  
Хочу сделать формирования запроса произвольных данных от сторонних приложений.
===========
И еще замечу, что если Вы исполняете скрипт для питона без jit либо трансляции в СИ,
то это раз в пять медленнее, чем на луа.
Спасибо, очень познавательно.
У меня задача немного проще сейчас: адаптировать существующего робота для работы с Quik. В принципе не сказать, что медленно, цикл проверок на триггер занимает около 50-150мс (вместе со всеми транзакциями). Для моих задач этого пока достаточно. В вашей системе какое время обработки получается?
Примерно  от 100 до 1000 раз быстрее.
Прикольно: Lua5.4 медленнее Lua5.3
 
а это python
Код
>pythonw -O "test.py" 
time=1.96  y=-94.5016299429584
>Exit code: 0
Прикольно: Lua5.4 медленнее Lua5.3
 
lua.jit без сюрпризов
Код
>D:/LuaJIT/luajit.exe -e "io.stdout:setvbuf 'no'" "testSM.jit" 
time=0.092   y=-94.501629942958
>Exit code: 0
Прикольно: Lua5.4 медленнее Lua5.3
 
Добрый день,
Тестил скорость питона, луа и jit и решил посмотреть, как ускорит Lua5.4 по сравнению 5.3.
--------------------
Раньше было быстрее, да и интернет говорит об этом же.
Выкладывал тест на форуме.
------------
Но получился прикол.
На этом тесте оказалось наоборот
Вот этот testSM.lua
Код
local V={}
local t=os.clock();
local N=256;
local y=0.;
local A=100.
local P=128
local W=2*3.14/N
for i=1,10000000 do
   y=A*math.sin(W*i);
end
local t1=os.clock()
print("time="..t1-t,"y="..y);

результат:
Код
>D:/lua54/lua54.exe -e "io.stdout:setvbuf 'no'" "testSM.lua" 
time=0.74   y=-94.501629942958
>Exit code: 0

>D:/lua53/lua53.exe -e "io.stdout:setvbuf 'no'" "testSM.lua" 
time=0.597   y=-94.501629942958
>Exit code: 0
Кто сможет объяснить?
Получение тиковых данных(исторических) во вне биржевой сессии
 
Цитата
Робеспьер написал:
Цитата
nikolz написал:
Да, тики - это лишь текущие торги. Свечи - на сервер КВИК формируются и хранятся 3000 шт. Если не будете удалять и переустанавливать, то будут накапливаться в арктве на компе бБлагодарю за пояснение
Благодарю за пояснение!
По поводу второго вашего поста, нужно было сделать только один запрос с последующим экспортом в cvs например, но теперь я понял что нужно искать другие источники биржевых данных, либо накапливать самому во внешнюю БД
Можно брать с финама
Ограничения при использовании QuikSharp.lua
 
Цитата
bespalex написал:
Цитата
перебор тоже вариант  
Чаще всего отключение происходит ровно в 10:00:05. Не знаю, может какое-то технологическое переключение в начале сессии, которое триггерит выкидыш. Не думаю, что если бы дело было в core.dll оно бы так выглядело.
Дело в том, что нет смысла передавать все данные из КВИК через луа в питон.
-------------
Моя концепция создания робота такая:
-----------
Робот условно содержит две части - я их назвал по аналогии с человеком - спинной и головной мозг.
Спинной - это все колбеки в КВИКЕ и все торговые операции в КВИКЕ.
Их нет смысла  перегонять в питон и обратно.
Это фактически автомат стандартных действий, которые не зависят никак от стратегии и тактики торговли.
Эту часть я реализую в КВИКЕ на луа + си for lua.
------------------
Головной мозг -  это прогнозы, управление капиталом, стратегии торговли можно и нужно реализовывать
в дополнительных потоках и приложениях  на любых языках, в том числе и питоне.
---------------------  
Вот для этого организую  взаимодействие КВИКа через Луа с python, rust,julia, terra, luajit и т д
================  
Сейчас обмен любыми данными делаю через mapping files.
Скорость обмена просто аховая, так как это обмен через память .
Нет никаких оберток. Поддерживаются все форматы.
Строки передаю как хеш.  Это фактически два целых числа.
Объем данных ограничен лишь объемом дисков.
----------------------  
Хочу сделать формирования запроса произвольных данных от сторонних приложений.
===========
И еще замечу, что если Вы исполняете скрипт для питона без jit либо трансляции в СИ,
то это раз в пять медленнее, чем на луа.
Получение тиковых данных(исторических) во вне биржевой сессии
 
Цитата
Робеспьер написал:
Всем привет!
Полагаю, что получение тиковых данных возможно только при активной биржевой сессии, или возможно, это от брокера зависит.
Код
  class_code  =   "TQBR" 
sec_code  =   "GAZP" 


 function   main ()
    ds, err  =   CreateDataSource (class_code, sec_code, INTERVAL_TICK)
     if  err ~ =   nil   then 
         message (tostring( message ))
         return 
     end 


    err  =  ds: SetEmptyCallback ()
     if  err  =  =   false   then 
         message (tostring(err))
         return 
     end 


     message ( string.format ( "Sizeof: %s" , ds: Size ()))
 end 


  

Вывод:
Sizeof: 0
При использовании свечного интервала, к примеру: INTERVAL_M1, наоборот данные возвращаются со всеми полями OHLC
у вас неправильно написана программа.
Надо один раз подписываться на источник, а не долбить сервер заявками на подписку. Сами тики приходят в колбек onAllTrade
----------------  
На форуме я выкладывал скрипт с очередью данных из колбеков и подпиской. посмотрите и повторите.
Получение тиковых данных(исторических) во вне биржевой сессии
 
Да, тики - это лишь текущие торги. Свечи - на сервер КВИК формируются и хранятся 3000 шт. Если не будете удалять и переустанавливать, то будут накапливаться в арктве на компе больше.
Стандартные индикаторы, Разместите стандартные индикаторы в терминал.
 
Мы , многонациональный народ России, достоин любого индикатора на халяву.
Поэтому  можем позаимствовать  у недружественных разработчиков алгоритм
и сделать на луа в КВИКЕ импортозамещение.  Как два пальца..
Cкорость обмена данными через файлы
 
Цитата
Kolossi написал:
Через файлы это хорошо, сам пользую. Как для передачи, так и для сохранения для последующего запуска. Вот только бэкапится приходится т.к. при коллизиях
и вывыливании терминала в дамп файлы частенько бьются. А поскольку в файл писать приходится часто это становится проблемой.
Как видно из экспериментов выше, время обмена через файлы,
особенно с отображением в память, меньше, чем вызов не сложной  функций на любом скриптовом языке.
---------------------
Но если это разные потоки или приложения, то надо синхронизировать, чтобы не было проблем.
------------------
Я предпочитаю синхронизацию без блокировки.
Проблем нет.
Cкорость обмена данными через файлы
 
Последний эксперимент - mapping files.
Создается файл, в который два скрипта пишут письма друг другу по очереди,
так же как во втором эксперименте.
---------------
Однако в этом случае. делается проекция файла в память. Приложения фактически обмениваются через память, при этом выполняется и запись в файл.
-------------
картинка работы приложений.




В файл каждое приложение выводит текущее время с квантом 0.1 мкс.
Для определения задержки обмена сообщения на экран отключены
Первое число - длина текста в строке
Результат в файле:
Код
23,171811.8128928,script2
23,171811.8128937,script1
23,171811.8128957,script2
23,171811.8128971,script1
23,171811.8128975,script2
23,171811.8128984,script1
23,171811.8128992,script2
23,171811.8129006,script1
23,171811.8129008,script2
23,171811.8129019,script1
23,171811.8129023,script2
23,171811.8129061,script1
23,171811.8129063,script2
23,171811.8129074,script1
23,171811.8129078,script2
23,171811.8129086,script1
23,171811.8129093,script2
23,171811.8129108,script1
23,171811.8129111,script2
23,171811.8129131,script1
23,171811.8129133,script2
23,171811.8129144,script1

Величина задержки определяется как разность времени соседних сообщений
Выборка из расчета задержки
Код
 0.900006853
 1.40001066
 0.900006853
 1.399981556
 1.100008376
 3.799999831
 1.099979272
 0.800006092

Величина задержки получилась менее  3 мкс.
-------------------  
Таким образом, при обмене не то что потоков, а приложений, через файлы с отображением в память
задержка сообщений не более 3 мкс.  
Cкорость обмена данными через файлы
 
если вывод сообщения на экран убрать, то время обмена сократится до 60 мкс.
Код
51.0,107,script 1
49.0,126,script 2
49.0,145,script 1
60.0,164,script 2
69.0,183,script 1
58.0,202,script 2
48.0,221,script 1
49.0,240,script 2
49.0,259,script 1
48.0,278,script 2
47.0,297,script 1
48.0,316,script 2
48.0,335,script 1
47.0,354,script 2
48.0,373,script 1
48.0,392,script 2
48.0,411,script 1
48.0,430,script 2
48.0,449,script 1
48.0,468,script 2
48.0,487,script 1
48.0,506,script 2
48.0,525,script 1
48.0,544,script 2
47.0,563,script 1
48.0,582,script 2
48.0,601,script 1
48.0,620,script 2
48.0,639,script 1
48.0,658,script 2
48.0,677,script 1
48.0,696,script 2
48.0,715,script 1
48.0,734,script 2
52.0,753,script 1
52.0,772,script 2
48.0,791,script 1
47.0,810,script 2
47.0,829,script 1
47.0,848,script 2
47.0,867,script 1
47.0,886,script 2
48.0,905,script 1
58.0,924,script 2
72.0,943,script 1
63.0,962,script 2
53.0,981,script 1
Cкорость обмена данными через файлы
 
Вот результаты теста обмена данными через файл двух приложений.
-----------------
Запускаю два приложения на луа.
Каждое приложение записывает свое сообщение в файл  в ответ на поступившее сообщение от другого приложения.
Поступившее сообщение выводится в окно приложения.
вот так это работает

а это содержимое файла через который выполняется обмен сообщениями
Первое число в строке - задержка между сообщениями в мкс.
Второе число - размер файла в данный момент.
В среднем задержка обмена составляет 0.2 ms или 0.0002 сек.
Код
277.0,91,script 2
274.0,110,script 1
271.0,130,script 2
271.0,150,script 1
271.0,170,script 2
245.0,190,script 1
243.0,210,script 2
402.0,230,script 1
403.0,250,script 2
366.0,270,script 1
361.0,290,script 2
358.0,310,script 1
352.0,330,script 2
345.0,350,script 1
348.0,370,script 2
301.0,390,script 1
268.0,410,script 2
232.0,430,script 1
228.0,450,script 2
228.0,470,script 1
227.0,490,script 2
153.0,510,script 1
153.0,530,script 2
146.0,550,script 1
149.0,570,script 2
154.0,590,script 1
155.0,610,script 2
152.0,630,script 1
150.0,650,script 2
150.0,670,script 1
149.0,690,script 2
149.0,710,script 1
148.0,730,script 2
150.0,750,script 1
179.0,770,script 2
187.0,790,script 1
162.0,810,script 2
150.0,830,script 1
148.0,850,script 2
146.0,870,script 1
165.0,890,script 2
186.0,910,script 1
166.0,930,script 2
146.0,950,script 1
147.0,970,script 2
149.0,990,script 1
148.0,1010,script 2
145.0,1031,script 1
147.0,1052,script 2
150.0,1073,script 1
147.0,1094,script 2
145.0,1115,script 1
148.0,1136,script 2
150.0,1157,script 1
149.0,1178,script 2
151.0,1199,script 1
153.0,1220,script 2
149.0,1241,script 1
147.0,1262,script 2
149.0,1283,script 1
147.0,1304,script 2
145.0,1325,script 1
147.0,1346,script 2
149.0,1367,script 1
147.0,1388,script 2
145.0,1409,script 1
148.0,1430,script 2
151.0,1451,script 1
148.0,1472,script 2
145.0,1493,script 1
147.0,1514,script 2
150.0,1535,script 1
151.0,1556,script 2
150.0,1577,script 1
156.0,1598,script 2
157.0,1619,script 1
147.0,1640,script 2
145.0,1661,script 1
148.0,1682,script 2
150.0,1703,script 1
148.0,1724,script 2
145.0,1745,script 1
182.0,1766,script 2
183.0,1787,script 1
148.0,1808,script 2
150.0,1829,script 1
147.0,1850,script 2
144.0,1871,script 1
147.0,1892,script 2
149.0,1913,script 1
147.0,1934,script 2
145.0,1955,script 1
148.0,1976,script 2
150.0,1997,script 1
147.0,2018,script 2
145.0,2039,script 1
148.0,2060,script 2
149.0,2081,script 1
147.0,2102,script 2
145.0,2123,script 1
147.0,2144,script 2
149.0,2165,script 1
147.0,2186,script 2
149.0,2207,script 1
152.0,2228,script 2
149.0,2249,script 1
148.0,2270,script 2
147.0,2291,script 1
147.0,2312,script 2
150.0,2333,script 1
184.0,2354,script 2
191.0,2375,script 1
208.0,2396,script 2
205.0,2417,script 1
203.0,2438,script 2
213.0,2459,script 1
216.0,2480,script 2
205.0,2501,script 1
203.0,2522,script 2
204.0,2543,script 1
203.0,2564,script 2
203.0,2585,script 1
203.0,2606,script 2
203.0,2627,script 1
203.0,2648,script 2
203.0,2669,script 1
201.0,2690,script 2
200.0,2711,script 1

Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
А это результат на сегодня.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата
Glukator написал:
Цитата
nikolz написал:
Хвалюсь.
------------------------------
Сегодня мой робот на сбере показал такую картинку с начала года.
 

Т е c 3.01.2024 профит   2.44%, из них 1.72 - лонг и 0.72 -шорт.
Стратегия "купил и держи" дала бы  1%.  
Чем тут хвалиться? Этой уродливой картинкой, по которой единственное, что можно понять, - что она опасна для глаз смотрящего?
У меня цыгане на соседней улице живут, так вот от их шмоток в глазах меньше рябит.
Это Ваша проблема. Сочувствую.
Ограничения при использовании QuikSharp.lua
 
Цитата
bespalex написал:
Цитата
nikolz написал:
 
Цитата
bespalex  написал:
QuikPy
 Если умеете программировать на луа и питон, то делаете обмен данными между приложением на питон и приложением на Луа. Либо ищите такой скрипт.
КВИК вообще при этом не требуется.
Потом скрипт луа для обмена запускаете в КВИК.
Не очень понял, т.к. QuikPy это и делает. Он работает на питоне в связке с QuikSharp, который запущен в QUIK. Вот между ними связь и теряется периодически.  
В документации QuikPy написано:
------------------
Возможные ошибки
  1. Если возникают ошибки, связанные с core.dll, то все варианты этой библиотеки выложены в проекте QUIKSharp
  2. Путем перебора подбираете подходящую для вас версию core.dll
  3. Если возникают ошибки при исполнении LUA скриптов, то, возможно, были обновления в QUIK или LUA. Последняя версия LUA скриптов находится  Они не учитывают мои специфические правки, но должны работать без ошибок с последней версией QUIK.
Успешного перебора.
Cкорость обмена данными через файлы
 
Добрый день,
Эта тема в основном для начинающих строителей роботов.
--------------------------
На вопрос  как сохранить или как передать данные в другой скрипт и приложение,
я рекомендую начать с обмена через файлы.
--------------------
Как правило в ответ получаю - через файлы - это медленно.
На вопрос -откуда Вы это знаете -обычно ответа нет.
----------------
Аналогичный вопрос возникает при попытке передать данные из одного приложения в другое.
---------------
Тем кто,  знает С for Lua, рекомендую mapping files, как самый универсальный и быстрый способ обмена,
если Вас не устраивает обычный обмен через файлы.
---------------
В этой теме я покажу как "медленно" реализуется обмен через файлы.
===============
Тест обмена через файлы в одном приложении.
-------------------
Написал вот такой тест:
Код
pD ="D:/QUIK_SCRIPT/nk_bot/Data/"
fn=pD..name..".log";  Log=io.open(fn,"w");
pDA ="D:/QUIK_SCRIPT/nk_bot/DataA/"
fnA=pDA..name..".log"; LogA=io.open(fnA,"w");
--------------------
local nF=nkevent.ccf(fn);
local nFA=nkevent.ccf(fnA);
local _,_,dHMS1=nkvm.D();
for j=1,100 do
     local _,_,dHMS=nkvm.D(); d=(1000000.*(dHMS-dHMS1))//1;
    Log:write(j..","..dHMS..","..d.."\n");Log:flush();
    while true do
   if nkevent.wcf(nF) then  dHMS1=dHMS; local  C=Log; Log=LogA; LogA=C; local x=nF; nF=nFA; nFA=x  break; end
   end
end
Что он делает?
Создаем на диске два каталога Data и DataA до запуска скрипта.
Скрипт открывает  в каждом из каталогов файл test.log.
-------------------
Далее в цикле 100 раз производится
запись с нечетным j в файл в Каталоге Data.
При обнаружении записи в файл , производим запись в файл в каталоге DataA по четным значениям j.
------------------
Таким образом, в файл каталога Data записываются ответы на запись в файл каталога DataA и наоборот.
---------------------
Каждая запись содержит значения j, текущее время и  задержку обнаружения записи в очередной файл.

Результат  Data/test.log:
Код
1,151047.6863891,790.0
3,151047.6865335,61.0
5,151047.6865586,10.0
7,151047.6865764,8.0
9,151047.6865931,8.0
11,151047.6866097,8.0
13,151047.6866333,15.0
15,151047.6866505,8.0
17,151047.6866669,8.0
19,151047.686683,8.0
21,151047.6866992,8.0
23,151047.6867155,8.0
25,151047.6867317,8.0
27,151047.6867478,8.0
29,151047.6867637,7.0
31,151047.6867809,8.0
33,151047.6867971,8.0
35,151047.6868131,8.0
37,151047.6868292,8.0
39,151047.6868453,8.0
41,151047.6868614,8.0
43,151047.6868775,8.0
45,151047.6868937,8.0
47,151047.6869098,8.0
49,151047.686926,8.0
51,151047.6869421,8.0
53,151047.6869583,8.0
55,151047.6869748,8.0
57,151047.6869909,8.0
59,151047.6870071,8.0
61,151047.687025,8.0
63,151047.6870415,8.0
65,151047.687059,8.0
67,151047.6870752,8.0
69,151047.6870911,8.0
71,151047.6871073,8.0
73,151047.6871234,8.0
75,151047.6871394,8.0
77,151047.6871554,8.0
79,151047.6871715,8.0
81,151047.6871876,8.0
83,151047.6872036,8.0
85,151047.6872198,8.0
87,151047.687236,8.0
89,151047.6872521,8.0
91,151047.6872683,8.0
93,151047.6872844,8.0
95,151047.6873004,8.0
97,151047.6873165,8.0
99,151047.6873325,8.0
Результат  DataA/test.log:
Код
2,151047.6864724,83.0
4,151047.6865484,14.0
6,151047.6865676,9.0
8,151047.6865849,8.0
10,151047.6866013,8.0
12,151047.6866179,8.0
14,151047.686642,8.0
16,151047.6866586,8.0
18,151047.6866749,8.0
20,151047.6866911,8.0
22,151047.6867072,7.0
24,151047.6867237,8.0
26,151047.6867397,8.0
28,151047.6867558,8.0
30,151047.6867727,8.0
32,151047.686789,8.0
34,151047.686805,7.0
36,151047.6868212,8.0
38,151047.6868372,7.0
40,151047.6868533,8.0
42,151047.6868695,8.0
44,151047.6868856,8.0
46,151047.6869017,8.0
48,151047.6869179,8.0
50,151047.686934,8.0
52,151047.6869502,8.0
54,151047.6869665,8.0
56,151047.6869828,8.0
58,151047.686999,8.0
60,151047.6870167,9.0
62,151047.6870333,8.0
64,151047.6870509,9.0
66,151047.687067,8.0
68,151047.6870831,7.0
70,151047.6870991,8.0
72,151047.6871153,8.0
74,151047.6871314,7.0
76,151047.6871474,8.0
78,151047.6871635,8.0
80,151047.6871795,8.0
82,151047.6871956,8.0
84,151047.6872116,7.0
86,151047.6872278,8.0
88,151047.687244,8.0
90,151047.68726,7.0
92,151047.6872763,8.0
94,151047.6872924,8.0
96,151047.6873085,8.0
98,151047.6873245,8.0
100,151047.6873405,8.0
Самое смешное то ,
что задержка измеряется в мкс
и составляет в среднем не более  10 . т.е. 0.000001 сек.
-------------------------
Это медленно?  
Запаздывание тиков
 
Добрый день,
Вопрос к разработчикам.
Можете объяснить, почему на учебном сервере тики приходят с запаздыванием от 500 до 1700 ms.
При этом задержка обмена по интернет не более 30 ms.
Задержка обработка колбека не более 0.1 ms
Вот результаты теста
строки с первым числом 2 - это обработка колбека onAllTrade.
Последнее число в строке(zT) - это задержка в ms
Я понимаю, что это учебный сервер, но у всего есть причина.
Хотелось бы понять и простить.
Код
4; 0.2, 22.6,AMEZ, 108,Ntpm=0
2,1.4; 163; MTLR,zT=712.0
2,0.2; 37; SBER,zT=712.0
2,0.1; 56; NKNC,zT=712.0
2,0.1; 27; MTSS,zT=712.0
2,0.1; 42; MTSS,zT=712.0
2,0.1; 24; MTSS,zT=712.0
2,0.1; 42; KAZT,zT=712.0
2,0.1; 31; VSMO,zT=712.0
2,0.1; 22; VSMO,zT=712.0
2,0.2; 25; TCSG,zT=1712.0
2,0.1; 20; TCSG,zT=1712.0
2,0.1; 26; TCSG,zT=1712.0
2,0.1; 30; TCSG,zT=1712.0
2,0.2; 23; TCSG,zT=1712.0
2,0.1; 24; MTLR,zT=1712.0
2,0.1; 34; SPBE,zT=1712.0
2,0.2; 41; SPBE,zT=1711.0
2,0.1; 25; SPBE,zT=1711.0
2,0.2; 32; SPBE,zT=1711.0
2,0.1; 41; BSPB,zT=1711.0
2,0.1; 25; BSPB,zT=1711.0
14; 0.2, 260.5,VSMO, 108,Ntpm=12
14; 0.2, 24.0,VKCO, 108,Ntpm=11
14; 0.2, 18.4,TCSG, 108,Ntpm=10
14; 0.2, 27.1,SPBE, 108,Ntpm=9
14; 0.1, 22.7,SGZH, 108,Ntpm=8
14; 0.2, 15.5,SBER, 108,Ntpm=7
14; 0.2, 15.3,ROSN, 108,Ntpm=6
14; 0.2, 154658.2,NKNC, 109,Ntpm=5
14; 0.4, 23.9,MTSS, 109,Ntpm=4
14; 0.3, 110.0,MTLR, 109,Ntpm=3
14; 0.2, 21.5,KMAZ, 109,Ntpm=2
14; 0.1, 150429.8,KAZT, 110,Ntpm=1
14; 0.4, 29.6,BSPB, 110,Ntpm=0
2,1.2; 179; SBER,zT=777.0
2,0.2; 30; SBER,zT=777.0
2,0.2; 23; SBER,zT=777.0
2,0.2; 23; SBER,zT=777.0
2,0.1; 23; SBER,zT=777.0
2,0.1; 21; SBER,zT=777.0
2,0.1; 22; SBER,zT=777.0
2,0.1; 24; SBER,zT=777.0
2,0.1; 27; SBER,zT=777.0
2,0.2; 44; SBER,zT=776.0
2,0.1; 22; SBER,zT=776.0
2,0.2; 21; SBER,zT=776.0
2,0.2; 22; SBER,zT=776.0
2,0.2; 22; SBER,zT=776.0
2,0.1; 22; SBER,zT=776.0
2,0.1; 19; SBER,zT=776.0
2,0.2; 20; SBER,zT=776.0
2,0.1; 22; SBER,zT=776.0
2,0.1; 21; SBER,zT=776.0
2,0.1; 38; SBER,zT=776.0
Ограничения при использовании QuikSharp.lua
 
Цитата
bespalex написал:
QuikPy
Если умеете программировать на луа и питон, то делаете обмен данными между приложением на питон и приложением на Луа. Либо ищите такой скрипт.
КВИК вообще при этом не требуется.
Потом скрипт луа для обмена запускаете в КВИК.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Хвалюсь.
------------------------------
Сегодня мой робот на сбере показал такую картинку с начала года.


Т е c 3.01.2024 профит   2.44%, из них 1.72 - лонг и 0.72 -шорт.
Стратегия "купил и держи" дала бы  1%.  
Тест времени подключения источников данных
 
Добрый день,
По просьбе разработчиков
https://forum.quik.ru/messages/forum10/message73569/topic8440/#message73569
выкладываю для общего пользования
свой тест измерения времени подключения источников данных.
Так как ранее использовался очень большой скрипт,
то пришлось написать специально тест для общего пользования.
-------------------
В тесте используется два таймера.
Один - мой на основе высокоточного счетчика OC на СИ. Выкладывал его на форуме.  Его квант 0.1мкс.
Второй - на основе socket. Для исключения сомнения в измерениях. Его квант 1 мс.
-------------------
Начинающие писатели роботов, можете позаимствовать мое решение организации очереди.
Код
--тест скорости подключения источников данных -автор nikolz
name="testnk"
paths = "D:/nkarray/"
package.cpath =paths.."?.dll";
require "nkarray"
p2 = "D:/luasocket/"
package.cpath =package.cpath ..";"..p2.."?.dll";
package.path =package.path..p2.."?.lua;"
socket = require("socket")
path = "D:\\QUIK_SCRIPT\\nk_bot\\"
Log=io.open(path..name..".log","w")
Ntp=0;    tp={}
local ds_int={INTERVAL_M1,INTERVAL_M5,INTERVAL_M30,INTERVAL_TICK};
function main()
   local t,int,tms,t1;
     while true do
      while Ntp>0 do
         t=tp[Ntp]; Ntp=Ntp-1 clas=t[1] sec=t[2]
         for i=1,#ds_int do ds={}
            t2=socket.gettime()*1000.
            nklib.startB();
            int=ds_int[i];
            local d,err; while d==nil do d,err=CreateDataSource(clas,sec,int); end
            d:SetEmptyCallback();
            t1=0.01*nklib.stopB();
            tms=(socket.gettime()*1000.-t2)//1
            Log:write("interval="..int..",sec="..tostring(sec)..",tnk="..t1.."мкс, tsocet="..(tms).."мc\n");Log:flush();
         end
      end
      sleep(1);
   end
end

function OnInit(pfile)  fconnect=isConnected(); end
function OnParam(c,s) Ntp=Ntp+1;    tp[Ntp]={c,s}; end
Это результаты работы теста на моем компе:
Код
interval=1,sec=VTBR,tnk=39.41мкс, tsocet=0.0мc
interval=5,sec=VTBR,tnk=20.17мкс, tsocet=0.0мc
interval=30,sec=VTBR,tnk=17.82мкс, tsocet=0.0мc
interval=0,sec=VTBR,tnk=13072.46мкс, tsocet=130.0мc

interval=1,sec=VSMO,tnk=57.81мкс, tsocet=0.0мc
interval=5,sec=VSMO,tnk=21.82мкс, tsocet=0.0мc
interval=30,sec=VSMO,tnk=21.73мкс, tsocet=0.0мc
interval=0,sec=VSMO,tnk=13581.32мкс, tsocet=135.0мc

interval=1,sec=UGLD,tnk=57.16мкс, tsocet=0.0мc
interval=5,sec=UGLD,tnk=25.99мкс, tsocet=0.0мc
interval=30,sec=UGLD,tnk=26.66мкс, tsocet=1.0мc
interval=0,sec=UGLD,tnk=12974.53мкс, tsocet=128.0мc

interval=1,sec=NMTP,tnk=57.63мкс, tsocet=0.0мc
interval=5,sec=NMTP,tnk=19.32мкс, tsocet=0.0мc
interval=30,sec=NMTP,tnk=17.54мкс, tsocet=0.0мc
interval=0,sec=NMTP,tnk=12912.37мкс, tsocet=129.0мc

interval=1,sec=VRSB,tnk=35.37мкс, tsocet=0.0мc
interval=5,sec=VRSB,tnk=27.25мкс, tsocet=0.0мc
interval=30,sec=VRSB,tnk=21.7мкс, tsocet=0.0мc
interval=0,sec=VRSB,tnk=12604.62мкс, tsocet=125.0мc

interval=1,sec=SIBN,tnk=34.2мкс, tsocet=0.0мc
interval=5,sec=SIBN,tnk=43.41мкс, tsocet=0.0мc
interval=30,sec=SIBN,tnk=18.91мкс, tsocet=0.0мc
interval=0,sec=SIBN,tnk=12793.29мкс, tsocet=127.0мc

Время подключения источников с интервалом 1,5,30 минут  составляет 30 мкс.
Время подключения тиков 12900 мкс. замедление в 400 раз.
==================
Демо сервер КВИК.
версия КВИК 11.1.0.45
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата
VPM написал:
nikolz, Наоборот прозрел, за скоростью не гоняюсь , тогда чем можно руководствоваться и как наилучшим (оптимальным) образом организовать память?
С памятью все просто.
-------------------
На диск надо писать лишь то, что хотите сохранить для истории и что не хранится в архивах КВИК.
Как правило - это результаты реальной торговли.  
Но и это можно не сохранять так как они есть в отчете брокера.
И только в отчете брокера Вы увидите что было реально.  
--------------------  
Кроме того, в отдельный файл можно записать исходные данные для торговли.  
Это позволяет не изменять их в скрипте.
-----------------  
Могу посоветовать следующее.
Написали что-то. Поставьте в начале блока N=os.clock()
и в конце time=os.clock()  -N  и выведите time в сообщение.   Вы узнаете сколько реально в секундах у вас выполняется этот блок. Если это разовый блок в начале запуска, то время вообще не колышет.
Если время вас устраивает, то забудьте про этот блок и пишите дальше.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
VPM,
Без обид, но Вы очевидно не представляете как реализована запись в файл в Винде. Если Вы часто читаете файл, то Вы читаете его из памяти, а не с диска. Поэтому разницы никакой нет. Да и вы же за скоростью не гонитесь.
Или что я упустил в Ваших рассуждениях?
Ограничения при использовании QuikSharp.lua
 
А зачем Вам QuikSharp? Его делали когда в КВИКЕ не было VMLua. В ту поры был смысл.
Сейчас смысла нет, кроме непонятных затыков.
Или я не прав?
Построение древа клиента
 
Цитата
Игорь Акименко написал:
Добрый день!

Коллеги, нужна помощь c lua. Не могу найти прямую зависимость.
То что хочу построить
firm_id (n1)
           - client_code (n1)
           ..........................
           - client_code (n)
                                      --trdaccid (n1)
                                      .....................
                                      --trdaccid (n)
firm_id (n)
           ..........................
           - client_code (n)
                                      .....................
                                      --trdaccid (n)


Есть ли зависимость такая? Как ее выстроить?

Проблема возникла из задачи определения кол-ва доступных стредств, если счет является " * -единый брокерский счет". Если я правильно понимаю сам факт проверки у нас есть через IsUcpClient.
Но возникает проблема когда к квику подключено несколько торговый счетов, фирма одна. При запросе лимитов при архитектуре древа, получается так что лимиты по деньгам дублируются, т.к. связь удалось выстроить только через фирму.

В целом реализацию делаю в питоне, посредством QuikSharp и библиотеки QuikPy. Но понять бы как это сделать на луа, можно бы было интерпретировать и в питоне.
Возможно кто то из вас уже реализовывал это и на самом питоне, буду очень признателен.
Есть. По таблицам и ключам с помощью функций для работы с произвольными таблицами.
Пишите и выкладывайте с конкретным вопросом.
Lua таблицу в файл и обратно
 
Преобразование таблицы Lua в строку, запись в файл и загрузка таблицы из файла в скрипт.
Код
function value2text(t,s)  --преобразование таблицы в скрипт
   local s1=""; --новое значение
   local n=string.len(s); local z=string.sub(s,n);
   local m= type(t);
   if m=="string" then
      s1='"'..tostring(t)..'"';  elseif m=="number" then s1=tonumber(t);  elseif t==nil then s1="nil";
   elseif m=="table" then local f;
      for j,v in pairs(t) do
         local x=v;
         if f then s1=s1.."," end  f=1;
         if  type(j)~="number" then    s1=s1..'\n["'..tostring(j)..'"]='; end
         s1=value2text(x,s1);
      end
      if z=='}' then s1='\n{'..s1..'}'; else s1='{'..s1..'}' end
   end
return s..s1;
end

--------------------  это пример вывода и загрузки с распечаткой значений из таблиц
local t2={6,7,8,9}
local t={1,2,3,4,5,"asd",t2}  -- это таблица которую выводим в файл
----------вывод в файл
local fn=p3.."test999.lua"
fLog=io.open(fn,"w"); fLog:write("t1="..value2text(t,"").."\n");fLog:flush()
fLog:close();
-----------ввод из файла
dofile(fn);
----------------прочитали таблицу из файла в таблицу t1
--теперь печатаем из введенной таблицы значения и сравниваем их со значениями в t2 и t
local t3=t1[7]
local s1=t1[6];
print(t1[1],s1,t3[3])

результат:
это содержимое файла test999.lua:
Код
t1={1,2,3,4,5,"asd",{6,7,8,9}}
это печать значений
Код
1   asd   8
Тормоз подключения тиков
 
Цитата
Nikolay написал:
Думается, что это проблема выбора реляционной базы для хранения данных (правда мой опыт обработки всех сделок, всех акций за 2016 год на MsSQL не вызывал каких-то проблем, кроме объема, но это год). Хотя организовать порционную подачу данных вполне можно. Заказали - начинают поступать данные. Если же сделано, что сначала все данные подготавливаются, кешируются и только потом выдаются всем объемом, то, наверно, это и приводит к таким задержкам. Плюс, видимо, у таких данных очень низкий приоритет, так что не во все пакеты попадают.  
Не понял, кто выбирает?
Тики вообще выдаются лишь за текущий день.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата
VPM написал:
Цитата
nikolz написал:
если Вы записали в файл fT таблицу T так, как она записана в скрипте Lua, то просто загрузите этот файл в скрипттак:loadfile(fT)
Я вообще не понимаю в чем различие loadfile от load в каком случае чем пользоваться (может есть какие то критерии) ???
load - загрузка из переменной string
loadfile - загрузка из файла на диске
=======================
Выкладываю для вас решение для вывода таблицы в файл и загрузки таблицы из  файла в скрипт
Код
function value2text(t,s)  --преобразование таблицы в скрипт
   local s1=""; --новое значение
   local n=string.len(s); local z=string.sub(s,n);
   local m= type(t);
   if m=="string" then
      s1='"'..tostring(t)..'"';  elseif m=="number" then s1=tonumber(t);  elseif t==nil then s1="nil";
   elseif m=="table" then local f;
      for j,v in pairs(t) do
         local x=v;
         if f then s1=s1.."," end  f=1;
         if  type(j)~="number" then    s1=s1..'\n["'..tostring(j)..'"]='; end
         s1=value2text(x,s1);
      end
      if z=='}' then s1='\n{'..s1..'}'; else s1='{'..s1..'}' end
   end
 return s..s1;
end

--------------------  это пример вывода и загрузки с распечаткой значений из таблиц
local t2={6,7,8,9}
local t={1,2,3,4,5,"asd",t2}  -- это таблица которую выводим в файл
----------вывод в файл
local fn=p3.."test999.lua"
fLog=io.open(fn,"w"); fLog:write("t1="..value2text(t,"").."\n");fLog:flush()
fLog:close();
-----------ввод из файла
dofile(fn);
----------------прочитали таблицу из файла в таблицу t1
--теперь печатаем из введенной таблицы значения и сравниваем их со значениями в t2 и t
local t3=t1[7]
local s1=t1[6];
print(t1[1],s1,t3[3])

результат:
это содержимое файла test999.lua:
Код
t1={1,2,3,4,5,"asd",{6,7,8,9}}
это печать значений
Код
1   asd   8
Тормоз подключения тиков
 
Цитата
Anton Belonogov написал:
nikolz, добрый день.

Увеличенное время объясняется разницей в запрашиваемом объеме данных.
Вообще-то после выхода из функции CreateDataSource ничего не загружено.
----------------------------
Загружается после.
--------------------------------
А ежели тики, да еще внутри сессии, то грузится несколько минут.
Очереди и двойные очереди в луа, Пример из книги Р.Е.
 
Цитата
VPM написал:
Glukator,  Я этим пользовался в lua 5.1 при переходе на 5.4 перестало работать, вот смысл:
Цитата
Используем преобразование таблицы в  текстовое представление  и сохраняем на диске результаты. -- Сохранение таблицы или массива в файл
function table.save(tbl,filename)
  local f,err = io.open(filename,"w")
  if not f then
     return nil,err
  end
  f:write( table.tostring (tbl))
  f:close()
  return true
end
В результате на диске мы получим файл, в котором в терминах синтаксика языка Lua описана наша таблица. Зачем сохранять в синтаксисе Lua? Причин две:   универсальность
 элегантный способ чтения таблицы из файла
  Вот функция, читающая файл и возвращающая сохранённую в нем таблицу: -- Чтение таблицы из файла в массива или таблицу
function table.read(filename)
  local f,err = io.open(filename,"r")
  if not f then
     return nil,err
  end
  local tbl = assert(loadstring("return " .. f:read("*a")))
  f:close()
  return tbl()
end
Все просто - читаем файл и запускаем его на выполнение    Вот как это выглядит: table.save({11,22,33,{"gh",'jk'},44},"e:\\1.dat")    -- пишем
t = table.read("e:\\1.dat")                                 -- читаем
 https://bot4sale.ru/blog-menu/qlua/301-save-lua-table.html
если Вы записали в файл fT таблицу T так, как она записана в скрипте Lua, то просто загрузите этот файл в скрипт
так:
loadfile(fT)
Страницы: Пред. 1 ... 10 11 12 13 14 15 16 17 18 19 20 ... 80 След.
Наверх