Показать сообщение отдельно
Старый 29.11.2011, 17:15   #49
HolyDel
 
Регистрация: 26.09.2006
Сообщений: 6,035
Написано 1,474 полезных сообщений
(для 2,707 пользователей)
Ответ: Великая битва 4х языков программирования на простейшей задачке

оно берется с кэша! Мока!

using System;
using System.Diagnostics;
using System.Threading;

namespace speedTest
{
    static class Program
    {
        public struct index
        {
            public int x, y, z;
        };

        static int Main()
        {
            int counter = 0;

            int count_values = 512 * 128 * 512;



            index[] ordered_values = new index[count_values];
            index[] random_values = new index[count_values];

            {
                int x = 0, y = 0, z = 0;
                Random r = new Random();

                for (int i = 0; i < count_values; ++i)
                {

                    ordered_values[i].x = z;
                    ordered_values[i].y = y;
                    ordered_values[i].z = x;

                    x++;
                    if (x > 511)
                    {
                        x = 0;
                        y++;
                    }
                    if (y > 127)
                    {
                        y = 0;
                        z++;
                    }


                    random_values[i].x = r.Next(511);
                    random_values[i].y = r.Next(127);
                    random_values[i].z = r.Next(511);
                }
            }
            Stopwatch timer = new Stopwatch();

            Thread.Sleep(100);

            { // Multidimensional 
                long elapsedAllocation, elapsedFill, elapsedGet, number;

                timer.Restart();

                int[, ,] map = new int[512, 128, 512];

                elapsedAllocation = timer.ElapsedTicks;
                Console.WriteLine("Multidimensional allocate: {0}ms", Math.Round(elapsedAllocation * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < 20; i++)
                {
                    for (int x = 0; x < 512; x++)
                    {
                        for (int y = 0; y < 128; y++)
                        {
                            for (int z = 0; z < 512; z++)
                            {
                                ++counter;
                                map[x, y, z] = counter;
                            }
                        }
                    }
                }

                elapsedFill = timer.ElapsedTicks;
                Console.WriteLine("Multidimensional fill: {0}ms", Math.Round((elapsedFill / 20f) * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[ordered_values[i].x, ordered_values[i].y, ordered_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Multidimensional get all times (ordered): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));

                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[random_values[i].x, random_values[i].y, random_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Multidimensional get all times (random): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));
            }

            Thread.Sleep(100);

            { // Flattened 
                long elapsedAllocation, elapsedFill, elapsedGet, number;

                timer.Restart();

                int[] map = new int[512 * 128 * 512];

                elapsedAllocation = timer.ElapsedTicks;
                Console.WriteLine("Flattened allocate: {0}ms", Math.Round(elapsedAllocation * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < 20; i++)
                {
                    for (int x = 0; x < 512; x++)
                    {
                        for (int y = 0; y < 128; y++)
                        {
                            for (int z = 0; z < 512; z++)
                            {
                                ++counter;
                                map[512 * 128 * x + 128 * y + z] = counter;
                            }
                        }
                    }
                }

                elapsedFill = timer.ElapsedTicks;
                Console.WriteLine("Flattened fill: {0}ms", Math.Round((elapsedFill / 20f) * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[512 * 128 * ordered_values[i].x + 128 * ordered_values[i].y + ordered_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Flattened get all times (ordered): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));

                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[512 * 128 * random_values[i].x + 128 * random_values[i].y + random_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Flattened get all times (random): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));
            }

            Thread.Sleep(100);

            { // Jagged 
                long elapsedAllocation, elapsedFill, elapsedGet, number;

                timer.Restart();

                int[][][] map = new int[512][][];
                for (int y = 0; y < 512; ++y)
                {
                    map[y] = new int[128][];

                    for (int z = 0; z < 128; ++z)
                    {
                        map[y][z] = new int[512];
                    }
                }

                elapsedAllocation = timer.ElapsedTicks;
                Console.WriteLine("Jagged allocate: {0}ms", Math.Round(elapsedAllocation * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < 20; i++)
                {
                    for (int x = 0; x < 512; x++)
                    {
                        for (int y = 0; y < 128; y++)
                        {
                            for (int z = 0; z < 512; z++)
                            {
                                ++counter;
                                map[x][y][z] = counter;
                            }
                        }
                    }
                }

                elapsedFill = timer.ElapsedTicks;
                Console.WriteLine("Jagged fill: {0}ms", Math.Round((elapsedFill / 20f) * 1000f / Stopwatch.Frequency, 3));
                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[ordered_values[i].x][ordered_values[i].y][ordered_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Jagged get all times (ordered): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));

                timer.Restart();

                for (int i = 0; i < count_values; ++i)
                {
                    number = map[random_values[i].x][random_values[i].y][random_values[i].z];
                }

                elapsedGet = timer.ElapsedTicks;
                Console.WriteLine("Jagged get all times (random): {0}ms", Math.Round(elapsedGet * 1000f / Stopwatch.Frequency, 3));
            }


            Console.Read();
            return 0;
        }
    }
}
вот вариант с последовательнам и рандомным доступом:
MD
allocate 6
fill 198
get(order) 149
get(rand) 956
FLAT
allocate 0.21
fill 39
get(order) 62.5 \ ??WTF
get(rand) 59.58 / ??WTF
JAGGED
allocate 210
fill 52
get(order) 92
get(rand) 677
Вложения
Тип файла: exe TestArraysAccess.exe (7.5 Кб, 639 просмотров)
(Offline)
 
Ответить с цитированием