Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2007.06.03;
Скачать: CL | DM;

Вниз

Можно ли как то оптимизировать данный участок кода   Найти похожие ветки 

 
DVM ©   (2007-05-09 14:36) [40]

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

Итак, было (510 fps):

for cy := 1 to ty do
 begin
   for cx := 1 to tx do
     begin
       inc(pmi^.blue, pc^.b);
       inc(pmi^.green, pc^.g);
       inc(pmi^.red, pc^.r);
       Inc(pc);
     end;
  inc(integer(pc), Delta);
end;


Стало (660 fps):


for cy := 1 to ty do
 begin
   b := 0; g := 0; r := 0;
   for CX := 1 to TX do
     begin
       inc(B, pc^.b);
       inc(g, pc^.g);
       inc(R, pc^.r);
       Inc(PC);
     end;
   mi.Blue := b; mi.Green := g; mi.Red := r;
   Inc(pmi.blue, mi.blue);
   Inc(pmi.green, mi.green);
   Inc(pmi.red, mi.red);
   inc(integer(pc), Delta);
 end;


Код стал странноват, но быстрее на 20 процентов.

Интересно, а еще быстрее можно?


 
oxffff ©   (2007-05-09 15:33) [41]


> Интересно, а еще быстрее можно?


Можно.

Software Optimization Guide for AMD Family 10h Processors
http://www.amd.com/us-en/assets/content_type/white_p…ch_docs/40546.pdf


 
Sapersky   (2007-05-09 22:43) [42]

А ведь все таки и твоя функция работает не совсем правильно, я сразу и не заметил.
Правильно работает, только если писать так:
procedure GetSum(var Src : PFColor; var Dst : PMatrixItem; Count : Integer);


Разумеется, указатель Src, если его передавать по значению (без var), после выполнения процедуры не инкрементируется. Ну а вручную инкрементировать трудно, что ли:
inc(integer(pc), Delta + tx * 3);
или вообще без указателей:
GetSum(@FDIB.Pixels24[cy, 1], @mi, tx);
т.к. во внешнем (вертикальном) цикле "ловить блох" не имеет смысла, да и TFastDIB.Pixels это не TBitmap.Pixels.

Интересно, а еще быстрее можно?

Можно всё-таки попробовать MMX... сейчас прикинул - получается 3 операции на пиксель вместо 6. Но для этого нужно:
1) Использовать 32-битные картинки вместо 24-битных. Или разложить 24 на 3 по 8, хотя это по многим причинам менее удобно.
2) Начало обрабатываемой области должно быть выравнено на 8 байт, т.е. на 2 пикселя, размер желательно тоже.
3) Обрабатывать за один вызов не более 65536 пикселей, т.к. размер счётчиков придётся сократить до word. Впрочем, это как раз не проблема.


 
DVM ©   (2007-05-09 23:01) [43]


> Разумеется, указатель Src, если его передавать по значению
> (без var), после выполнения процедуры не инкрементируется.
>

Да, я уже понял. Собственно меня вариант без использования доп процедуры даже больше устраивает.


> Можно всё-таки попробовать MMX...


> Использовать 32-битные картинки вместо 24-битных.

Не, отпадает - при конвертации/разложении потеряем весь прирост скорости.


 
Fenik ©   (2007-05-10 15:06) [44]

> DVM ©
> for cy := 1 to ty do
>  begin
>    b := 0; g := 0; r := 0;
>    for CX := 1 to TX do
>      begin
>        inc(B, pc^.b);
>        inc(g, pc^.g);
>        inc(R, pc^.r);
>        Inc(PC);
>      end;
>    mi.Blue := b; mi.Green := g; mi.Red := r;
>    Inc(pmi.blue, mi.blue);
>    Inc(pmi.green, mi.green);
>    Inc(pmi.red, mi.red);
>    inc(integer(pc), Delta);
>  end;

А что такое mi? Может проще:

   Inc(pmi.blue, b);
   Inc(pmi.green, g);
   Inc(pmi.red, r);

а то 3 лишних присваивания.


 
Fenik ©   (2007-05-10 15:06) [45]

> DVM ©
> for cy := 1 to ty do
>  begin
>    b := 0; g := 0; r := 0;
>    for CX := 1 to TX do
>      begin
>        inc(B, pc^.b);
>        inc(g, pc^.g);
>        inc(R, pc^.r);
>        Inc(PC);
>      end;
>    mi.Blue := b; mi.Green := g; mi.Red := r;
>    Inc(pmi.blue, mi.blue);
>    Inc(pmi.green, mi.green);
>    Inc(pmi.red, mi.red);
>    inc(integer(pc), Delta);
>  end;

А что такое mi? Может проще:

   Inc(pmi.blue, b);
   Inc(pmi.green, g);
   Inc(pmi.red, r);

а то 3 лишних присваивания.


 
DVM ©   (2007-05-10 15:18) [46]


> а то 3 лишних присваивания.

:) Они не лишние. Так вот быстрее чуть-чуть, как ни странно. К тому же они находятся во внешнем цикле - поэтому пофиг.


 
Knight ©   (2007-05-10 16:13) [47]

> [46] DVM ©   (10.05.07 15:18)

А если..

   b := pc^.b; g := pc^.g; r := pc^.r;
   for CX := 2 to TX do
     begin
       Inc(PC);
       inc(b, pc^.b);
       inc(g, pc^.g);
       inc(R, pc^.r);
     end;

Или что-то в этом направлении...


 
DVM ©   (2007-05-10 16:20) [48]


> Knight ©   (10.05.07 16:13) [47]

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


 
Knight ©   (2007-05-10 16:24) [49]

> [48] DVM ©   (10.05.07 16:20)

Разве три присваивания нулей и три inc-а быстрее чем просто присваивание первых элементов и переход сразу ко вторым?


 
Knight ©   (2007-05-10 16:41) [50]

[49] Да ещё помноженное на ty внешнего цикла...


 
Knight ©   (2007-05-10 16:57) [51]

А если несколько потоков запускать? %)


 
DVM ©   (2007-05-10 17:36) [52]


> А если несколько потоков запускать? %)

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


 
Sapersky   (2007-05-10 18:00) [53]

Ради интереса сделал-таки с MMX, только макс. кол-во обрабатываемых за вызов пикселей - 256, а не 65536, прочие условия см. [42]. Быстрее где-то в 1.2 раза.
Вот, может пригодится:

Type
 PMatrixItem16 = ^TMatrixItem16;
 TMatrixItem16 = record
   Blue, Green, Red, Alpha: Word;
 end;

procedure GetSumMMX(Src : PFColorA; Dst : PMatrixItem16; Count : Integer);
asm
 shr ecx, 1
 jz @exit

 db $0F,$EF,$D2           /// pxor mm2, mm2
 db $0F,$EF,$DB           /// pxor mm3, mm3
 db $0F,$EF,$E4           /// pxor mm4, mm4
@loop:
 db $0F,$6F,$00           /// movq mm0, [eax]
 db $0F,$6F,$C8           /// movq mm1, mm0
 db $0F,$60,$CA           /// punpcklbw mm1, mm2
 db $0F,$68,$C2           /// punpckhbw mm0, mm2
 db $0F,$FD,$D8           /// paddw mm3, mm0
 db $0F,$FD,$E1           /// paddw mm4, mm1
 add eax, 8
 dec ecx
jnz @loop
 db $0F,$FD,$DC           /// paddw mm3, mm4
 db $0F,$7F,$1A           /// movq [edx], mm3
@exit:
end;

После цикла с обработкой:
asm
 db $0F,$77               /// emms
end;


 
DVM ©   (2007-05-10 18:07) [54]


> Sapersky   (10.05.07 18:00) [53]

спасибо, погляжу



Страницы: 1 2 вся ветка

Текущий архив: 2007.06.03;
Скачать: CL | DM;

Наверх




Память: 0.57 MB
Время: 0.056 c
15-1178300863
vasya123123
2007-05-04 21:47
2007.06.03
Свой инсталлятор / installer


15-1178698333
Kerk
2007-05-09 12:12
2007.06.03
Ищу единомышленников...


15-1178201448
Root.Square.Root
2007-05-03 18:10
2007.06.03
Элементарно!


2-1179217468
voe
2007-05-15 12:24
2007.06.03
Проблемы с DBComboBox


2-1179133124
dobry
2007-05-14 12:58
2007.06.03
отображение memo поля