Feedback

Leistung inkrementieren; For-For Schleifen

Sprache: C#

Guten Tag, ich war durch ein Video(https://www.youtube.com/watch?v=B4DuT61lIPU) aufmerksam gemacht worden, Code so weit optimieren zu können, dass die Leistung um (in meinem Beispiel) circa 16% inkrementiert werden kann. Man denke, man habe ein Bild(2-Dimensional), und deklariert und initialisiert sie in einem 1-Dimensionalem Array(Merke: 1-Dimensionale Arrays sind expressis verbis schneller als 2-Dimensionale Arrays) Will man nun über die Index-Formel x + y * WIDTH auf das Element k zugreifen(durch Iteration), so muss gelten, dass x als erstes iteriert wird. Soll heißen, y + 1, wenn x == WIDTH und nicht x + 1 wenn y == HEIGHT. Warum? Wenn wir uns betrachten: Wir iterieren y als erstes, dann gilt (WIDTH exemplarisch 2048) for x = 0 to width for y = 0 to height Index = x + y * WIDTH (y = 1) (x = 0) Index = 0 + 1 * 2048 = 2048. next next Das heißt, dass die üblichen 2047 Elemente geladen, aber nicht benutzt und verworfen werden(!). Abhilfe schafft sequenzielles Iterieren: for y = 0 to HEIGHT for x = 0 to WIDTH Index = x + y * WIDTH Index = 1 + 0 * 2048 = 1 next next Index bei x = 1 ist 1(!). Nur 1(!) Element wird geladen. Ein Codebeispiel in C#
//‏بسم الله الرحمن الرحيم ‎

//developed by ~3r0rXx


public Color GetColor(Texture2D Texture) //XNA/MONOGAME 
{
Color[] __chace = new Color[Texture.Width * Texture.Height];
Color[] __copier = new Color[255 + 255 + (255 * 1)];
int[] __chace1 = new int[255 + 255 + (255 * 1)];
 
Func<byte, byte, byte, int, long> hash = (byte r__in, byte g__in, byte b__in, int n) =>
{
	var h = 0L;
	for (byte i = 0; i < 1; i++)
	{
		h = r__in + g__in + (b__in * i);
	}
	return h;
};

Texture.GetData<Color>(__chace);

      int __index = 0;
            int __max = __chace1[__index];
            for (int j = 0; j < Texture.Height; j++)
            {
                for (int i = 0; i < Texture.Width; i++)
                {
                    var c = __chace[i + j * Texture.Width];
                    var h = hash(c.R, c.G, c.B, Texture.Width * Texture.Height);
                    __chace1[h]++;
                    __copier[h] = c;
                    if (__chace1[h] > __max)
                    {
                        __max = __chace1[h];
                        __index = (int)h;
                    }
                }
            }

return __copier[__index];
}

//Ergebnis im Release Mode
//0.06 ms

//Dasselbe mit y-Erst-Iteration
//0.35 ms
//‏بسم الله الرحمن الرحيم ‎

//developed by ~3r0rXx


public Color GetColor(Texture2D Texture) //XNA/MONOGAME 
{
Color[] __chace = new Color[Texture.Width * Texture.Height];
Color[] __copier = new Color[255 + 255 + (255 * 1)];
int[] __chace1 = new int[255 + 255 + (255 * 1)];
 
Func<byte, byte, byte, int, long> hash = (byte r__in, byte g__in, byte b__in, int n) =>
{
	var h = 0L;
	for (byte i = 0; i < 1; i++)
	{
		h = r__in + g__in + (b__in * i);
	}
	return h;
};

Texture.GetData<Color>(__chace);

      int __index = 0;
            int __max = __chace1[__index];
            for (int j = 0; j < Texture.Height; j++)
            {
                for (int i = 0; i < Texture.Width; i++)
                {
                    var c = __chace[i + j * Texture.Width];
                    var h = hash(c.R, c.G, c.B, Texture.Width * Texture.Height);
                    __chace1[h]++;
                    __copier[h] = c;
                    if (__chace1[h] > __max)
                    {
                        __max = __chace1[h];
                        __index = (int)h;
                    }
                }
            }

return __copier[__index];
}

//Ergebnis im Release Mode
//0.06 ms

//Dasselbe mit y-Erst-Iteration
//0.35 ms