Здравствуйте, гость ( Вход | Регистрация )

35 страниц V « < 7 8 9 10 11 > »   
Ответить в эту темуОткрыть новую тему
> Помогите освоить LUA
sutra
сообщение 21.11.2018, 2:25
Сообщение #161


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Заставил себя всё-таки ещё полопатить свой файнд. Результаты есть, удалось добиться ещё прироста в скорости почти в полтора раза. Скрипт подлатаю и выложу позже, на него сейчас без слёз не взглянешь. Но возникли вопросы.
Сишные переменные не прокатили в двух операторах, может опять чего не так делаю?
local _,_,r1,r2=usl:find("R%((%d+)%-*(%d*)")
r1,r2=tonumber(r1),tonumber(r2)

Обозвал их так: local s=ffi.new("uint8_t[9]")

Пришлось уже после их выполнения делать так:
s[0],s[1],s[2],s[3],s[4],s[5]=r1,r2,g1,g2,b1,b2

Возможно несовместимый тип, я так думаю.

local m=ffi.new("int16_t[6]")
m[0]=tonumber(r1)
log(m[0])

Да, вот так нормально, в общем надо ещё полопатить.

И то не факт, этот тип как я понял, только положительные значения. Надо наверное uint16 использовать.

И ещё вопрос. А не массивом, а обычными переменными как обозвать через ffi ?

И есть ли смысл? Может лучше массивом и оставить?
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 21.11.2018, 6:52
Сообщение #162


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Цитата
local _,_,r1,r2=usl:find("R%((%d+)%-*(%d*)")
r1,r2=tonumber(r1),tonumber(r2)

Код
local r1,r2=usl:match("R%((%d+)%-*(%d*)")
r1,r2=tonumber(r1),tonumber(r2)

Тоже самое без возврата начала и конца позиции, которые и так в _ пишутся.
Цитата
s[0],s[1],s[2],s[3],s[4],s[5]=r1,r2,g1,g2,b1,b2

Возможно несовместимый тип, я так думаю.

Тут пишутся double, хорошо если не string в char. Т.е. у нас следующая проблема:
Дано: 64 бита с плавающей точкой.
Задача: запихать 64 бита с плавающей в 8 бит целочисленных.
В целом если значение мешье или равно 255 все пройти должно нормально. Но тут должно быть приведение типов. Все значения удолетворяют этому условию? Успешное расширение до int16_t намекает, что там значения больше, чем 255.
Цитата
Надо наверное uint16 использовать.

Конкретно в вашем случае можно и знаковый тип использовать. Главное чтобы значение помеситлось. Беззнаковые были зачастую намного тормознутее - это настораживает, хотя 16 битные при сложении подобных проблем не показали.
Цитата
А не массивом, а обычными переменными как обозвать через ffi ?

По сути там все идет через оператор выделения памяти - new(), который обычно только для массивов вызвается в явном виде, хотя где-то в недрах, наверное, вызывается и при инициализации переменной.
Переменная, значение ей задали 10:
local my_var = ffi.new("int",10)

Переменная, значение не задано, но так лучше не делать, хороший тон хотя бы NULL туда помещать.
local my_var = ffi.new("int")
my_var = 10 -- приводит к тому, что она из cdata становится number.
Вообще подобная конвертация из cdata в number мне не понятна. Более того даже из примера https://luajit.org/ext_ffi.html так же становится number не смотря на то, что это элементы таблицы. Но и этого даже мало - спокойно дает переполнить переменную без каких либо ошибок. Что при это происходит в реальности и в каком типе находятся данные не ясно. Скорее всего если оставлять все в рамках, то все будет хорошо и типы не будут приводиться, тем не менее странно как-то это все.


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 21.11.2018, 7:03
Сообщение #163


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Код
local arr_uchar = ffi.new("unsigned char[10]", 2)

arr_uchar[0] = 1200

for i = 0, 9 do
    log (arr_uchar[i], type(arr_uchar[i]))
end

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


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 22.11.2018, 15:12
Сообщение #164


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Цитата
local r1,r2=usl:match("R%((%d+)%-*(%d*)")

Спасибо Дарк, начал шаг за шагом "вылизывать" код.

Код
--lua
function Find1(usl)
  local _,_,r1,r2=usl:find("R%((%d+)%-*(%d*)")
  local _,_,g1,g2=usl:find("G%((%d+)%-*(%d*)")
  local _,_,b1,b2=usl:find("B%((%d+)%-*(%d*)")
  local _,_,RG1,RG2=usl:find("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local _,_,RB1,RB2=usl:find("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local _,_,GB1,GB2=usl:find("G%-B%[(%-*%d+)%s*(%-*%d*)")
end
function Find2(usl)
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
end

log "clear" log "mode compact"
tmm = os.clock()
for i=1, 1000000 do
  Find1("R(7-155)B(8-154)G(9-153)R-G[50 90]R-B[60 80]G-B[70 75]")
end
log(os.clock()-tmm)    -- среднее 3,137 сек
tmm = os.clock()
for i=1, 1000000 do
  Find2("R(7-155)B(8-154)G(9-153)R-G[50 90]R-B[60 80]G-B[70 75]")
end
log(os.clock()-tmm)    -- среднее 2,829 сек
tmm = os.clock()


Стало эстетичнее и на 10% быстрее (для этого участка кода).
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 22.11.2018, 17:01
Сообщение #165


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Попытка переделать блок инициализации в СИ-шные переменные потерпела фиаско. tonumber с СИ-шной переменной работает только если строка реально является числом (по крайней мере я так понял). Поэтому перед вызовом tonumber пришлось анализировать строки и это привело к падению производительности.
Код
--lua
local ffi = require "ffi"
function Find1(usl)
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
  r1,r2=tonumber(r1),tonumber(r2)
  g1,g2=tonumber(g1),tonumber(g2)
  b1,b2=tonumber(b1),tonumber(b2)
  RG1,RG2=tonumber(RG1),tonumber(RG2)
  RB1,RB2=tonumber(RB1),tonumber(RB2)
  GB1,GB2=tonumber(GB1),tonumber(GB2)
  if r1==nil then  r1,r2=0,255  else  if r2==nil then  r2=r1  end  end
  if g1==nil then  g1,g2=0,255  else  if g2==nil then  g2=g1  end  end
  if b1==nil then  b1,b2=0,255  else  if b2==nil then  b2=b1  end  end
  if RG1==nil then  RG1,RG2=-255,255  else  if RG2==nil then  RG2=255  end  end
  if RB1==nil then  RB1,RB2=-255,255  else  if RB2==nil then  RB2=255  end  end
  if GB1==nil then  GB1,GB2=-255,255  else  if GB2==nil then  GB2=255  end  end
end
function Find2(usl)
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
  local s=ffi.new("uint8_t[6]")
  local m=ffi.new("int16_t[6]")
  if r1==nil then s[0],s[1]=0,255
  else
    s[0]=tonumber(r1)
    if r2=="" then s[1]=s[0]  else s[1]=tonumber(r2)  end
  end
  if g1==nil then s[2],s[3]=0,255
  else
    s[2]=tonumber(g1)
    if g2=="" then s[3]=s[2]  else s[3]=tonumber(g2)  end
  end
  if b1==nil then s[4],s[5]=0,255
  else
    s[4]=tonumber(b1)
    if b2=="" then s[5]=s[4]  else s[5]=tonumber(b2)  end
  end
  if RG1==nil then m[0],m[1]=-255,255
  else
    m[0]=tonumber(RG1)
    if RG2=="" then m[1]=255  else m[1]=tonumber(RG2)  end
  end
  if RB1==nil then m[2],m[3]=-255,255
  else
    m[2]=tonumber(RB1)
    if RB2=="" then m[3]=255  else m[3]=tonumber(RB2)  end
  end
  if GB1==nil then m[4],m[5]=-255,255
  else
    m[4]=tonumber(GB1)
    if GB2=="" then m[5]=255  else m[5]=tonumber(GB2)  end
  end
end

log "clear" log "mode compact"
tmm = os.clock()
for i=1, 1000000 do
  Find1("R(7-155)B(8-154)G(9-153)R-G[50 90]R-B[60 80]G-B[70 75]")
end
log(os.clock()-tmm)    -- 3.480 сек. и 3.569 сек.
tmm = os.clock()
for i=1, 1000000 do
  Find2("R(7-155)B(8-154)G(9-153)R-G[50 90]R-B[60 80]G-B[70 75]")
end
log(os.clock()-tmm)    -- 4.774 сек. и 4.866 сек.
tmm = os.clock()
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 22.11.2018, 18:38
Сообщение #166


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Точнее к падению производительности привело преобразование типов при выполнении tonumber.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 22.11.2018, 20:32
Сообщение #167


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Код
--lua
local ffi = require "ffi"
local rmem = ffi.cast
ffi.cdef[[
typedef struct { uint16_t x; uint16_t y; uint8_t red; uint8_t green; uint8_t blue; } rgba_pixel;
]]
function FindRGBold(addr,len,scrX1,scrY1,fx1,fy1,fx2,fy2,usl,numf)
  local n=math.min(numf,(fx2-fx1+1)*(fy2-fy1+1))
  local arr = ffi.new("rgba_pixel[?]", n )
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
  r1,r2=tonumber(r1),tonumber(r2)
  g1,g2=tonumber(g1),tonumber(g2)
  b1,b2=tonumber(b1),tonumber(b2)
  RG1,RG2=tonumber(RG1),tonumber(RG2)
  RB1,RB2=tonumber(RB1),tonumber(RB2)
  GB1,GB2=tonumber(GB1),tonumber(GB2)
  if r1==nil then  r1,r2=0,255  else  if r2==nil then  r2=r1  end  end
  if g1==nil then  g1,g2=0,255  else  if g2==nil then  g2=g1  end  end
  if b1==nil then  b1,b2=0,255  else  if b2==nil then  b2=b1  end  end
  if RG1==nil then  RG1,RG2=-255,255  else  if RG2==nil then  RG2=255  end  end
  if RB1==nil then  RB1,RB2=-255,255  else  if RB2==nil then  RB2=255  end  end
  if GB1==nil then  GB1,GB2=-255,255  else  if GB2==nil then  GB2=255  end  end
  local k,indY,ind,r,g,b=-1
  for i=fy1,fy2 do
    indY=addr+(i-scrY1)*len
    for j=fx1,fx2 do
      ind=indY+(j-scrX1)*3
      b=rmem("unsigned char*", ind)[0]
      g=rmem("unsigned char*", ind+1)[0]
      r=rmem("unsigned char*", ind+2)[0]
      if r>=r1 and r<=r2 and g>=g1 and g<=g2 and b>=b1 and b<=b2 and r-g>=RG1 and r-g<=RG2 and r-b>=RB1 and r-b<=RB2 and g-b>=GB1 and g-b<=GB2 then
        k=k+1 arr[k].x, arr[k].y, arr[k].red, arr[k].green, arr[k].blue = j,i,r,g,b
        if numf==k then  return arr, k  end
      end
    end
  end
  return arr, k
end
function FindRGB(addr,len,scrX1,scrY1,fx1,fy1,fx2,fy2,usl,numf)
  local n=math.min(numf,(fx2-fx1+1)*(fy2-fy1+1))
  local arr = ffi.new("rgba_pixel[?]", n )
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
  r1,r2=tonumber(r1),tonumber(r2)
  g1,g2=tonumber(g1),tonumber(g2)
  b1,b2=tonumber(b1),tonumber(b2)
  RG1,RG2=tonumber(RG1),tonumber(RG2)
  RB1,RB2=tonumber(RB1),tonumber(RB2)
  GB1,GB2=tonumber(GB1),tonumber(GB2)
  if r1==nil then  r1,r2=0,255  else  if r2==nil then  r2=r1  end  end
  if g1==nil then  g1,g2=0,255  else  if g2==nil then  g2=g1  end  end
  if b1==nil then  b1,b2=0,255  else  if b2==nil then  b2=b1  end  end
  if RG1==nil then  RG1,RG2=-255,255  else  if RG2==nil then  RG2=255  end  end
  if RB1==nil then  RB1,RB2=-255,255  else  if RB2==nil then  RB2=255  end  end
  if GB1==nil then  GB1,GB2=-255,255  else  if GB2==nil then  GB2=255  end  end
  local s,m=ffi.new("uint8_t[9]"),ffi.new("int16_t[6]")
  s[0],s[1],s[2],s[3],s[4],s[5],m[0],m[1],m[2],m[3],m[4],m[5]=r1,r2,g1,g2,b1,b2,RG1,RG2,RB1,RB2,GB1,GB2
  local k,indY,ind,r,g,b=-1
  for i=fy1,fy2 do
    indY=addr+(i-scrY1)*len
    for j=fx1,fx2 do
      ind=indY+(j-scrX1)*3
      s[8]=rmem("unsigned char*", ind)[0]
      s[7]=rmem("unsigned char*", ind+1)[0]
      s[6]=rmem("unsigned char*", ind+2)[0]
      if s[6]>=s[0] and s[6]<=s[1] and s[7]>=s[2] and s[7]<=s[3] and s[8]>=s[4] and s[8]<=s[5] and s[6]-s[7]>=m[0] and  -- ПЕРЕНЕС УСЛОВИЕ. ФОРУМ ЛОМАЛО.
             s[6]-s[7]<=m[1] and s[6]-s[8]>=m[2] and s[6]-s[8]<=m[3] and s[7]-s[8]>=m[4] and s[7]-s[8]<=m[5] then
        k=k+1 arr[k].x,arr[k].y,arr[k].red,arr[k].green,arr[k].blue=j,i,s[6],s[7],s[8]
        if numf==k then  return arr, k  end
      end
    end
  end
  return arr, k
end
function ImageToArray(addr,len,scrX1,scrY1,fx1,fy1,fx2,fy2)
  local n=(fx2-fx1+1)*(fy2-fy1+1)
  local arr = ffi.new("rgba_pixel[?]", n )
  local s=ffi.new("uint8_t[3]")
  local k,indY,ind,r,g,b=-1
  for i=fy1,fy2 do
    indY=addr+(i-scrY1)*len
    for j=fx1,fx2 do
      ind=indY+(j-scrX1)*3
      s[2]=rmem("unsigned char*", ind)[0]
      s[1]=rmem("unsigned char*", ind+1)[0]
      s[0]=rmem("unsigned char*", ind+2)[0]
      k=k+1 arr[k].x,arr[k].y,arr[k].red,arr[k].green,arr[k].blue=j,i,s[0],s[1],s[2]
    end
  end
  return arr, k
end

log "clear" log "mode compact"
local addr, width, height, len = getimage (0, 0, 999, 999)
local vi, k={}
tmm = os.clock()
for i=1, 1000 do
  vi,k=FindRGBold(addr,len,0,0,0,0,999,999,"G-B[0 255]",10000000)
end
log(os.clock()-tmm)  -- 22.037 сек.
tmm = os.clock()
for i=1, 1000 do
  vi,k=FindRGB(addr,len,0,0,0,0,999,999,"G-B[0 255]",10000000)
end
log(os.clock()-tmm)   --15.357 сек.
tmm = os.clock()
for i=1, 1000 do
  vi,k=ImageToArray(addr,len,0,0,0,0,999,999)
end
log(os.clock()-tmm)   --7.139 сек.

Вроде как конечный вариант, если нужно просто получить массив, лучше использовать отдельную функцию. У меня получилось 140 миллионов пикселей в секунду, но результат наверное сильно зависит от камушка.

Сообщение отредактировал DarkMaster - 23.11.2018, 6:14
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 22.11.2018, 21:27
Сообщение #168


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Цитата
local _,_,RG1,RG2=usl:find("R%-G%[(%-*%d+)%s*(%-*%d*)")
local _,_,RB1,RB2=usl:find("R%-B%[(%-*%d+)%s*(%-*%d*)")
local _,_,GB1,GB2=usl:find("G%-B%[(%-*%d+)%s*(%-*%d*)")
end
function Find2(usl)
local r1,r2=usl:match("R%((%d+)%-*(%d*)")
local g1,g2=usl:match("G%((%d+)%-*(%d*)")
local b1,b2=usl:match("B%((%d+)%-*(%d*)")

Почему такое принципиальное нежелание использовать таблицы, а не строку для передачи параметров?


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 23.11.2018, 1:08
Сообщение #169


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Цитата
Почему такое принципиальное нежелание использовать таблицы, а не строку для передачи параметров?

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

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

Цитата
у меня нет вызовов файнда в цикле

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


Хотя, что-то мне подсказывает, что в ближайшее время тебе будет не до примеров. (IMG:style_emoticons/default/rolleyes.gif)
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 23.11.2018, 1:29
Сообщение #170


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



И опять же, я же не зря потестил всё. Полноценный разбор строки составляет менее 300 микросекунд. Даже на дохлом камне и то это всё мгновенно будет, ну а Cirus-а вообще наверное всё должно летать. Хотя если научите, конечно сделаю и таблицей.

В принципе получилась замечательная вещь. Я переделал свой распознаватель текста и уверен, что могу сделать любой распознаватель, который с помощью вот такого файнда будет всё распознавать намного быстрее, чем делается getimage.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 23.11.2018, 2:42
Сообщение #171


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Вот если бы ещё и getimage через ffi прикрутить, вот это была бы суперскорость, только сдаётся мне что получить доступ к окну быстро всё равно не получится, наверняка всё делается как обычно через "третьи" руки, а значит однозначно тормоза.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 23.11.2018, 6:11
Сообщение #172


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Цитата

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

Дык я же писал. Ща еще раз (IMG:style_emoticons/default/smile.gif)
Код
function FindRGBold(addr,len,scrX1,scrY1,fx1,fy1,fx2,fy2,usl,numf)
  local n=math.min(numf,(fx2-fx1+1)*(fy2-fy1+1))
  local arr = ffi.new("rgba_pixel[?]", n )
  local r1,r2=usl:match("R%((%d+)%-*(%d*)")
  local g1,g2=usl:match("G%((%d+)%-*(%d*)")
  local b1,b2=usl:match("B%((%d+)%-*(%d*)")
  local RG1,RG2=usl:match("R%-G%[(%-*%d+)%s*(%-*%d*)")
  local RB1,RB2=usl:match("R%-B%[(%-*%d+)%s*(%-*%d*)")
  local GB1,GB2=usl:match("G%-B%[(%-*%d+)%s*(%-*%d*)")
end

-- Usl у нас теперь таблица, а не строка.
-- Задаем только те параметры которые нужны.
-- Остальные можно дописать в теле таблицы умолчательными.
local usl = {r1=10, r2=12, GB2=32}

-- Объявление функции не меняется. Тело:
function FindRGBold(addr,len,scrX1,scrY1,fx1,fy1,fx2,fy2,usl,numf)
  local r1 = usl.r1
  local r2 = usl.r2
  local g1 = usl.g1
  local g2 = usl.g2
...
  local GB2 = usl.GB2

На самом деле, как вы уже, наверное догадались, смысла в подобном присвоении, немного и на самом деле можно напрямую использовать usl.r1 и другие параметры. В стандартном случе не требующим большой производительности это действительно было бы так. В нашем же случае все более требовательно. Поясню:
Код
local arr = {10,11,22} -- мы создали одномерный массив на 3 элемента. Это именно массив, находящийся одним неразрывным куском в памяти.
log (arr[1]) -- вывод первого элемента массива, отсчет с единицы.
local t = {first=10, second=11, third = 22} -- мы создали таблицу, которая размазана по памяти.
log (t.first) -- вывод первого элемента таблицы.

А теперь собственно главное:
arr[1] и t.frist - какая разница кроме написания? Разница во времени обращения. Она отличается в 1.7 раза (по данным luajit.org).
Дело в реализации данных конструкций.
arr - как я уже говорил это просто кусок памяти, где последовательно записаны значения. Отсюда и скорость работы с ним.
t - это массив _ключей_ аналогичный arr и ссылок на данные. Т.е. в случае с t у нас в памяти одним куском записан массив структур:
ключ1 = адрес_данных1, ключ2 = адрес_данных2, ключ3 = адрес_данных3
Соответственно, чтобы получить непосредственно данные приходится искать нужный ключ в массиве, потом считывать адрес и только потом получать данные.
Массивы быстрее, если необхоимо последовательно обрабатывать данные последовательно (наш случай).
Работа с таблицами бывает быстрее, если необходимо удалять/добавлять объекты не в конце/начале массива. В случае с массивом он должен будет полностью перестроен в памяти заново, в случае же с таблице перестроен будет только массив ключей (может и не перестроен, зависит от реализации).
Скорость переменных относительно массивов не знаю, не тестил.
Немного теории которая может быть не актуальной из-за особенностей реализации и jit оптимизации. Есть очень важный момент - чем больше таблица тем медленнее работает поиск ключа. Какое отношение это имеет к переменным? В lua самое прямое. Даже если вы объявлете переменную, то на самом деле объявляете элемент скрытой таблицы. В луа все является таблицей. Для увеличения быстродействия может быть полезно не создавать много переменных, а часть данных помещать в таблицу, т.к. созданные переменные будут неизбежно замедлять общую скорость работы. Я когда-то давно обнаружил в lua подобное снижение производительности и даже на форуме с cirus это обсуждал. Там что-то было про регекспы и os.clock(). Вопрос на тот момент остался повисшим и тогда причин я не знал, тесты не все были полностью однозначными и производительность явно "гуляла". Гуляла она скорее всего из-за изменения порядка переменных в скрытой таблице луа (порядок элементов там не гарантируется).


И так мы задали часть параметров таблицей local usl = {r1=10, r2=12, GB2=32}. Все параметры мы писать едва ли захотим, да и читаемость будет не очень. Нам нужно задать параметры по умлчанию. Тут есть два основных пути:
Задание параметров по умолчанию вариант 1
-- Проверяем существует ли поле в таблице, если нет, то присваиваем значение по умолчанию.
Код
local r1 = usl.r1 or 10

or и and можно использовать не самым очевидным образом в луа. Эти операторы на самом деле возрващают значения.
var1 or var2 работает следующим образом:
Код
if var 1 then
    return var1
else
    return var2
end

var1 and var2 работает следующим образом:
Код
if var 1 then
    return var2
else
    return var1
end

Способ хороший, наглядный.


Задание параметров по умолчанию вариант 2

Мы можем наглым образом объявить значения таблицы, а потом перезаписать имеющимися:
Код
local function fcolor(my_var)
    local var = {n1=1, n2=2, n3=3, n4=4}    
    for k, v in next, my_var do  -- Перебираем все ключи и значения таблицы t2
        local var[k]=v           -- Подменяем значение с таким же ключем.
    end
end

local my_var = {n2=20, n3 = 30}
fcolor(my_var)

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



Можно пойти дальше и довести все до логичного завершения - поместить все эти данные в массив или структуру Си. Ну это у вас уже реализовано. Хотя лично мне кажется более логичным сначала создать структуру, а потом уже непосредственно в нее помещать данные не создавая временные lua переменные r1-GB2. Не забываем, что они могут замедлить выполнение всей функции. В идеале я бы вообще в рамках функции которая осуществляет непосредственный перебор оставил только одну си-структуру или си-массив, чтобы исключить все возможные проблемы.
Структура си, по идее не должна иметь разницы по скорости относительно массива си не смотря на то, что поля там текстовые, читаемость повысится.

Сообщение отредактировал DarkMaster - 23.11.2018, 7:30


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 23.11.2018, 9:58
Сообщение #173


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Цитата
В идеале я бы вообще в рамках функции которая осуществляет непосредственный перебор оставил только одну си-структуру или си-массив

Я тоже конечно думал на эту тему. Но, как я уже говорил, мой опыт в СИ - нулевой, ну и главный демотиватор - мне просто жаль убивать своё время, его не так много осталось, а овчинка выделки не стоит. В идеале можно вообще полностью с нуля написать свою программу, НО ЗАЧЕМ? Если у нас уже есть Пилот, который в подавляющем большинстве случаев делает свою работу "на ура". У меня была всего одна проблема - скорость при обработке динамично меняющегося изображения, я её с твоей и божьей помощью с блеском решил. Да и проблема то во многом была из-за пост-обработки (анализа данных) изображения. При переходе на lua - проблема "ПОСТ" - просто исчезла. Спасибо Дарк, что потратил на меня столько времени, я многому научился.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 23.11.2018, 10:11
Сообщение #174


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Скорость обработки порядка 40 кадров в секунду меня более чем устраивает. Перелопачивание массивов пикселей требовалось только при распознавании символов, но там требования к скорости были не критичны, хотя и в этом направлении результат получился супер. До сих пор пока ещё запускаю параллельный скрипт и то время выполнения менее 3 сотых сек. Так что пока наверное я остановлюсь на достигнутом. Надо скрипт переделывать на lua, а скрипт ой какой не хилый, думаю даже за месяц не управлюсь.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 23.11.2018, 14:04
Сообщение #175


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Цитата
а овчинка выделки не стоит.

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

Маленький совет. Все финдколоры, финдимиджи выносить сразу в шапку скрипта в отдельную таблицу, открытие менюшек тоже делать таблицу с функциями. Это уже просто шишки набитые. Все равно в итоге придете к этому либо бардак будет. Слишком много однотипной писанины, а вызов финдов в этой писанины потом к проблемам приводит, т.к. одинаковый финд может быть востребован в нескольких местах, а при изменении области/погрешностей выискивать каждый финд заново бывает запарно и высока вероятность появления двух разных по содержанию финдов ищущих одно и то же.
local fi, fc, open, click = {},{},{},{}
Это у меня из сохраненного шаблона скрипта.


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 7.12.2018, 5:47
Сообщение #176


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Не дождался я фикса на findimage, нацарапал свой, используя СИ-шные переменные. Ещё раз огромное спасибо Дарку. Доморощенный, без наворотов findimage работает примерно в 130 раз быстрее (100 раз искал картинку в цикле поиска 26 картинок - всего 0.009 сек). Кстати, у Кнайта скорость ОЧЕНЬ сильно зависит от параметра deviation, чем он больше, тем медленнее. А этот параметр я использую практически всегда. Мне не совсем понятно почему такая зависимость, видимо шибко хитрый и мудрёный алгоритм.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 7.12.2018, 13:54
Сообщение #177


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Всё-таки офигительную штуку подсказал мне Дарк. Раньше при многоступенчатом выборе тех или иных действий приходилось выставлять ожидание до 300 миллисекунд после клика, для гарантированной связи с сервером и отрисовки нового изображения на экране. Теперь сделал собственную функцию LeftWait, которая перед кликом запоминает определённую область экрана и после клика - ждёт обновления экрана, прежде чем вернуться в основное тело скрипта. Результат? Теперь всё просто "летает", ждёт ровно столько, сколь нужно.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
DarkMaster
сообщение 7.12.2018, 16:54
Сообщение #178


***********

Модератор UOPilot
Сообщений: 9.465
Регистрация: 2.12.2008
Группа: Супермодераторы
Наличность: 27681
Пользователь №: 11.279



Цитата
Теперь сделал собственную функцию LeftWait, которая перед кликом запоминает определённую область экрана и после клика - ждёт обновления экрана, прежде чем вернуться в основное тело скрипта. Результат? Теперь всё просто "летает", ждёт ровно столько, сколь нужно.

Это при условии, что приложение нормальное. Частенько клики проходят через раз, вместо одного окна выбивает другое, слишком ранние контрольные клики приводят к морганию новых окон, быстрые клики к зависанию (IMG:style_emoticons/default/crazy.gif) Так что могу поздравить с приложением (IMG:style_emoticons/default/smile.gif)
А что не так было в финдимидже то? Он работает на ура. Проблемы некоторые есть с координатами из-за рамки, вроде проблемы еще были при поиске через getimege (координаты съезжали), но там можно было ручками фикисть да и вроде уже исправлено. У меня этот метод просто засунут в другой скрипт который постоянно используется, а потроха я уже точно не помню, как именно используют его.


--------------------
Скрипты UOPilot под заказ.
Консультации по UOpilot 15$/час.
Услуги Lua разработчика (не пилот, проекты, постоянка)
Disсоrd:
Kov____
Пользователь в онлайне!Delete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 7.12.2018, 23:00
Сообщение #179


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Цитата
А что не так было в финдимидже то?

Ну cirus показывал что не так. И по скорости очень много вопросов. Точно по "нужной" области финд работает некорректно, приходится расширять зону поиска, а это приводит к потере скорости. Как я говорил, у меня есть ситуации, когда приходится ставить deviation 6%, можешь потестить сам и удивишься, как сильно падает производительность, в своём финде, мне наплевать какая разница в цветовых каналах, я даже сам не ожидал такой скорости, ну очень быстро. Я знаю где лежит искомая область для картинки, и для такого случая, когда не надо "бороздить просторы мирового экрана" поиск осуществляется практически мгновенно. Например для Сайрусовского распознавателя текстов при помощи картинок - это был бы прорыв.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения
sutra
сообщение 7.12.2018, 23:15
Сообщение #180


*******

Adept
Сообщений: 923
Регистрация: 10.8.2018
Группа: Пользователи
Наличность: 0
Пользователь №: 19.007



Цитата
Частенько клики проходят через раз

Я понял причину таких моментов, опыт, опыт и опыт. Начинаю понимать что и как работает. Для себя понял одно ... Всему есть причина, только нужно её понять. У меня все проблемы возникают вследствие многозадачности среды, т.е. когда я сам ещё чего-то делаю, то конечно может понадобиться первичная активация рабочего окна, прежде чем кликнуть результативно. В общем есть такие моменты, решаю просто, сначала (обычно делают в конце) "контрольный" клик, например в заголовок рабочего окна, без всякой паузы сразу же рабочий клик. Ну пока всё работает ну просто на ура. Спасибо тебе Дарк, всё летает, всё круто, я сам в шоке от результатов.
Пользователь в офлайнеDelete PostОтправить личное сообщение
Вернуться в начало страницы
+Ответить с цитированием данного сообщения

35 страниц V « < 7 8 9 10 11 > » 
Ответить в эту темуОткрыть новую тему
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 

- Текстовая версия | Версия для КПК Сейчас: 20.4.2024, 3:30
Designed by Nickostyle