Ich würde zuersteinmal das Format auf 32Bit umstellen, weil 32Bit-Werte vom Prozessor in der regel schneller verarbeitet werden können (auf 32Bit-systemen) als 24Bit-Werte.
Ich würde vor der eigentlichen Optimierung aber deinen Code umstrukturieren!
Zuersteinmal solltest du den Aufbau der Funktion zu überdenken, d.h. versuchen, den Code sinnvoll in Subfunktionen auszulagern. Es gibt sehr viele Codeblöcke die durch Copy&Paste entsatnden sind. Copy&Paste ist immer ein starkes Anzeichen dafür, dass man den Code ausgliedern sollte. Bitte gib deinen Variablen aussagekräftigere Namen. Dein aktueller Code ist trotz Kommentierung für einen Außenstehenden schwer nachzuvollziehen.
Fangen wir mal an, aufzuräumen:
Ich frage mich z.B., warum du die Variablen col2 - col8 hast, aber nie direkt benutzt, sondern immer in c1 und c2 kopierst. Ich vermute, du hast den Code mehrfach kopiert und eingefügt, und warst zu faul ihn zu verändern. Genau aus diesem Grund gibt es Sub-Routinen! Performanceeinbußen sind dadurch in der Regel nicht zu erwarten, weil die Funktion vom Compiler in der Regel ge-inlined werden sollte, wenn nicht, kann man dies durch
function MyFunction(...); inline;
erzwingen.
Das hier ließe sich super ausgliedern:
Delphi-Quellcode:
c1:=col2;
c2:=col4;
if (c1<>col5) and (c2<>col5) and (col5=background) then begin
b4[x*3+2]:=(getrvalue(c1)+getrvalue(c2)+getrvalue(col5)*relevance) div (3+relevance);
b4[x*3+1]:=(getgvalue(c1)+getgvalue(c2)+getgvalue(col5)*relevance) div (3+relevance);
b4[x*3+0]:=(getbvalue(c1)+getbvalue(c2)+getbvalue(col5)*relevance) div (3+relevance);
end;
{ ... weiterer gleichartiger Code ...}
Hier mein (ungetesteter) Code:
Delphi-Quellcode:
function GetAntialiasedValue(Center, Value1, Value2: Byte; {relevance:integer}): byte; inline;
// relevance ist auskommentiert, muss man nicht unbedingt als Parameter übergeben
begin
result := (Value1+Value2+Center*relevance) div (3+relevance);
end;
procedure ProcessPixel(PixelPointer: PByte; Center, Color1, Color2: TColor); inline;
begin
PixelPointer := GetAntialiasedValue(GetBValue(Center), GetBValue(Color1), GetBValue(Color2));
inc(PixelPointer);
PixelPointer^ := GetAntialiasedValue(GetGValue(Center), GetGValue(Color1), GetGValue(Color2));
inc(PixelPointer);
PixelPointer^ := GetAntialiasedValue(GetRValue(Center), GetRValue(Color1), GetRValue(Color2));
end;
...
if col5 = background then
begin
if (col2<>col5) and (col4<>col5) then begin
ProcessPixel(@b4[x*3], col5, col2, col4);
if (col2<>col5) and (col6<>col5) then begin
ProcessPixel(@b4[x*3], col5, col2, col6);
if (col8<>col5) and (col6<>col5) then begin
ProcessPixel(@b4[x*3], col5, col8, col6);
if (col8<>col5) and (col6<>col5) then begin
ProcessPixel(@b4[x*3], col5, col8, col6);
end;
Siehst du, wie viel übersichtlicher das ganze jetzt ist? Dadurch wird es viel einfacher, Optimierungen durchzuführen, weil man zusammenhängenden Code immer sofort mit einem Blick erfassen kann. Z.B. fällt nun das häufige
@b4[x*3] auf: Hier könnte man stattdessen einen Pointer benutzen, denn man nach jedem Durchlauf der x-Schleife um 3 (bzw 4, bei 32Bit) erhöht. Zudem habe ich die if-Abfragen verschachtelt, sodass die weiteren Abfragen nicht mehr durchgeführt werden müssen, wenn die erste bereits False ergibt. Auch dies ist ein Schluss, der durch die bessere Übersichtlichkeit begünstigt wurde. Desweiteren sparst du durch die Funktionen eine Menge Variablen!
Das ganze ist natürlich noch nicht fertig, bis jetzt wurde auch noch nicht viel optimiert. Als nächstes würde ich wie gesagt versuchen, von den Arrays wegzukommen, und stattdessen komplett auf Pointer umzustellen, was wohl noch am ehesten einen Geschwindigkeitsschub geben sollte. Ansonsten kann hier wohl nicht mehr sehr viel Performance herausgeholt werden. Trotzdem ist ein "Refactoring" sinnvoll, um den Code verständlicher zu machen. Wenn du dir deine alte Funktion in einem Jahr anguckst, wirst du dich erst einmal eine haleb Stunde lang einarbeiten müssen, damit du wieder weißt, was der Code eigentlich macht... ich spreche da aus eigener Erfahrung!
Also vereinfache das ganze noch ein bisschen, vielleicht fällt dir noch die ein oder andere Optimierungsmöglichkeit dabei auf.