— Расширение для внешних функций, массивов и переменных, задаваемых в правилах инструкции *.ini
— Например, для {tag.line.func(arg,...), n} или {VAR[ind1,...]} или {VAR} реально происходит
— обращение к функции func(id, tag, line, index-n, org, ...) или к элементу массива VAR[id][ind1]… или VAR[id]
— id — имя секции (CR_TD в примере), tag — идентификатор графика (CR_m15), line — номер линии графика (по умолчанию 0),
— index — номер свечи (с 1). Возможен простой вариант вызова функции {func()}
— LbotTest.ini
--[CR_TD]
--; Используется внешняя функция sma() и переменная SMA_LENGTH
--Security = CRH5, SPBFUT, CR_m15, TD
--OpenLong = {CR_m15.0.sma(20), 1} > 0 and {SMA_LENGTH} < 3
--CloseLong = {sma(20), 1} < 0 or {SMA_LENGTH} > 5
— LbotExternal.lua
SMA_LENGTH = {} — счетчик свечей между изменениями направленности SMA
local SMA = {}
— Определяет направленность скользящей среднней
function sma(id, tag, line, index, period)
if not SMA[id] then
SMA[id] = {}
SMA_LENGTH[id] = {}
end
if not SMA[id][period] then
SMA[id][period] = {}
end
if SMA[id][period].LastIndex == index then
return SMA[id][period].LastValue
end
SMA[id][period].LastIndex = index
local c, n = getCandlesByIndex(tag, 0, index — 1, 1)
if n ~= 1 then
message('ОШИБКА при вызове sma3() для '… tag, 3)
end
local b = c[0]
SMA[id][period][index] = b.close
local value
if index > 2 * period then
local sma1 = 0
for i = index, index — period + 1, -1 do
if SMA[id][period][i] then
sma1 = sma1 + SMA[id][period][i]
end
end
sma1 = sma1 / period
local sma2 = 0
for i = index — period, index — 2 * period + 1, -1 do
if SMA[id][period][i] then
sma2 = sma2 + SMA[id][period][i]
end
end
sma2 = sma2 / period
local value0 = SMA[id][period].LastValue
value = sma1 — sma2
SMA[id][period].LastValue = value
— Проверка на смену направленности
if not value0 or value * value0 < 0 then
SMA_LENGTH[id] = 1
else
SMA_LENGTH[id] = SMA_LENGTH[id] + 1
end
local dt = b.datetime
--message(dt.day… '.'… dt.month… '.'… dt.year… ' '… dt.hour… ':'… dt.min)
--message('LastValue='… SMA[id][period].LastValue)
end
return value
end
------------------------------------------------------------------
---------------------------------------------------------------------------------------
local getCBar = getConcBar
— Выборка лучшего из 32 инструментов по RSI
local TGS32 = { 'SBER_d_r', 'GAZP_d_r', 'LKOH_d_r', 'YDEX_d_r', 'MGNT_d_r', 'GMKN_d_r', 'ALRS_d_r',
'NVTK_d_r', 'ROSN_d_r', 'CHMF_d_r', 'NLMK_d_r', 'AFKS_d_r', 'PLZL_d_r', 'SNGSP_d_r',
'PHOR_d_r', 'MOEX_d_r', 'TRNFP_d_r', 'TATNP_d_r', 'MTSS_d_r', 'IRAO_d_r', 'FEES_d_r',
'RTKMP_d_r', 'VTBR_d_r', 'SPBE_d_r', 'HYDR_d_r', 'RASP_d_r', 'SIBN_d_r', 'OGKB_d_r',
'TGKA_d_r', 'MRKP_d_r', 'MSNG_d_r', 'NMTP_d_r' }
function r32(id, tag, line, index)
local MEDIUM = 16
local tg = tag… '_r'
local n = getNumCandles(tg)
if n == 0 then
message('r32() ОШИБКА Отсутствует график '… tg, 3)
return 0
end
local b, n = getCandlesByIndex(tg, line, index — 1, 1)
if n ~= 1 then
message('r32() ОШИБКА Отсутствует значение №'… index… ' графика '… tg, 3)
return 0
end
b = b[0]
local c = b.close
local rate = 1
local exists
local p, k = 0, 0
if c > 50 then
p = p + 1
elseif c < 50 then
k = k + 1
end
for _, tg1 in pairs(TGS32) do
if tg1 and tg1 ~= tg then
local b1 = getCBar(tag, index — 1, tg1, line)
--local b1 = getConcBar(tag, index, tg1, line)
if b1 then
local c1 = b1.close
if c1 > 50 then
p = p + 1
elseif c < 50 then
k = k + 1
end
exists = true
if c > c1 then
rate = rate + 1
end
end
end
end
assert(exists, 'r32() ОШИБКА Отсутствуют сравниваемые значения для графика '… tg)
local dt = b.datetime
if dt.year == 2025 and dt.month == 2 and dt.day == 9 and dt.hour >= 9 then
message(dt.day… '.' .. dt.month… '.'… dt.year… ' '… dt.hour… ':'… dt.min)
message('r='… tg… ' c='… c… ' rate='… rate)
end
local rm
if p >= MEDIUM then
rm = p
elseif k <= MEDIUM then
rm = -k
else
rm = 0
end
if rm < 0 then
rate = rate — #TGS32 — 1
end
return rate
end
------------------------------------------------------------------
local getCBar = getConcBar — Для чтения параллельной свечи сравниваемого инструмента
— Выборка лучшего инструмента по RSI (*_h4_r)
local TGS = { 'Si_h4_r', 'CR_h4_r', 'Eu_h4_r', 'GL_h4_r', 'BR_h4_r', 'NA_h4_r', 'RI_h4_r', 'MM_h4_r', 'NG_h4_r', 'GD_h4_r'
, 'SV_h4_r', 'SF_h4_r', 'ED_h4_r', 'SR_h4_r', 'GZ_h4_r', 'RN_h4_r', 'SN_h4_r', 'LK_h4_r', 'VB_h4_r', 'YD_h4_r'
, 'TI_h4_r', 'MN_h4_r', 'ME_h4_r', 'GK_h4_r', 'TT_h4_r', 'AL_h4_r', 'PZ_h4_r', 'AF_h4_r', 'NK_h4_r', 'AK_h4_r'
, 'MT_h4_r', 'PI_h4_r', 'CH_h4_r', 'VK_h4_r' }
local MEDIUM = 17
function best34(id, tag, line, index)
local tg = tag… '_r'
local n = getNumCandles(tg)
if n == 0 then
message('best34() ОШИБКА Отсутствует график '… tg, 3)
return 0
end
local b, n = getCandlesByIndex(tg, line, index — 1, 1)
if n ~= 1 then
message('best34() ОШИБКА Отсутствует значение №'… index… ' графика '… tg, 3)
return 0
end
b = b[0]
local c = b.close
local rate = 1
local exists
local k = 0 — Счетчик падающих инструментов (нужен для отрицательного rate)
if c < 50 then
k = k + 1
end
index = index — 1
for _, tg1 in pairs(TGS) do
if tg1 and tg1 ~= tg then
local b1 = getCBar(tag, index, tg1, line)
if b1 then
local c1 = b1.close
if c1 < 50 then
k = k + 1
end
exists = true
if c > c1 then
rate = rate + 1
end
end
end
end
assert(exists, 'best34() ОШИБКА Отсутствуют сравниваемые значения для графика '… tg)
if k > MEDIUM then
rate = rate — #TGS — 1
end
return rate
end