OberonCore

Библиотека  Wiki  Форум  BlackBox  Компоненты  Проекты
Текущее время: Четверг, 28 Март, 2024 11:41

Часовой пояс: UTC + 3 часа




Начать новую тему Ответить на тему  [ Сообщений: 7 ] 
Автор Сообщение
СообщениеДобавлено: Среда, 19 Октябрь, 2011 16:56 
Аватара пользователя

Зарегистрирован: Пятница, 25 Ноябрь, 2005 18:55
Сообщения: 2272
Откуда: Россия, Нижний Новгород
Обнаружил следующую непонятную вещь...

Сначала введение

Пару лет назад я озаботился сравнением скорости работы разных процессоров. Хотелось узнать какой процессор быстрее. Я написал простенькую програмку, которая O(N^2) способом сортирует массив из 65535 целых чисел и замеряет время. Какой процессор быстрее эту програмку выполнит, тот и лучше. Написал я её на C#.
Код:
         private void Safe ()
         {
            const int n = 65535;
            int[] a = new int[n];
            int i, j;
            i = 0;
            while (i < n)
            {
               a[i++] = i * 1524231 + 27736188;
            }
            i = 0;
            while (i < n)
            {
               j = 0;
               while (j < n)
               {
                  if (a[j] < a[i])
                  {
                     int t = a[i];
                     a[i] = a[j];
                     a[j] = t;
                  }
                  j++;
               }
               i++;
            }
         }
Однако, так как Mono заметно уступает Microsoft.Net, то когда я запускал эту програмку на компьютерах с линуксом, то их производительность оказывалась чуть хуже, чем могла бы быть если бы Mono не уступала Microsoft.Net. Тогда я написал эту же самую сортировку в unsafe кодах, то есть не через индексы массива, а через указатели. Фактически на Си-подмножестве языка C#.
Код:
         private unsafe void Unsafe ()
         {
            const int n = 65535;
            int* a = stackalloc int[n];
            int* e = a + n;
            int* p, q;
            int i = 0;
            while (i < n)
            {
               a[i++] = i * 1524231 + 27736188;
            }
            p = a;
            while (p < e)
            {
               q = a;
               while (q < e)
               {
                  if (*q < *p)
                  {
                     int t = *p;
                     *p = *q;
                     *q = t;
                  }
                  q++;
               }
               p++;
            }
         }
Скорость работы unsafe программы в большей степени зависела от качества процессора чем от качества дотнета. Я не ставил своей целью сравнивать safe и unsafe код по быстродействию, я мерил разные процессоры. Совершенно очевидно было что unsafe код всегда выполнится быстрее чем safe код. Например, на Core i7 860 если производительность по unsafe коду принять за единичку, то производительность по safe коду совершенно естественно окажется меньше - 0.89. На Athlon 64 X2 4200+ практически тоже самое. При unsafe=1 для safe получаем 0.88.

А теперь необъяснимые чудеса...

На процессоре Core i5 2300 под 64 разрядной Windows 7 (дотнет 4.0) если производительность по unsafe коду принять за единичку, то производительность по safe коду чудесным образом окажется не меньше, а больше - 1.22.

Почему на этом компьютере сэйфный код выполняется на 22% быстрее ансэйфного аналога?..

-------------------------------------------------------
Доп. инфо.: программа скомпилирована под дотнет 3.5.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Среда, 19 Октябрь, 2011 17:05 
Аватара пользователя

Зарегистрирован: Пятница, 25 Ноябрь, 2005 18:55
Сообщения: 2272
Откуда: Россия, Нижний Новгород
Если кому интересно померить свой процессор, вот проект для Студии, там же уже скомпилированный дотнетный бинарник
Вложение:
Комментарий к файлу: Проект для Студии
Performance2.zip [34.81 КБ]
Скачиваний: 351


Код:
Core i7 860 2.8ГГц 4 ядра, DDR3 1333, Windows 7 64bit
-------------------------------------------------------------------
 threads |  mode  | normalized performance | absolute performance |
-------------------------------------------------------------------
       1 | unsafe |                   1,00 |                 3,54 |
       1 |  safe  |                   0,89 |                 3,17 |
-------------------------------------------------------------------
       2 | unsafe |                   1,97 |                 6,98 |
       2 |  safe  |                   1,78 |                 6,31 |
-------------------------------------------------------------------
       3 | unsafe |                   3,00 |                10,60 |
       3 |  safe  |                   2,69 |                 9,51 |
-------------------------------------------------------------------
       4 | unsafe |                   3,65 |                12,91 |
       4 |  safe  |                   2,98 |                10,54 |
-------------------------------------------------------------------
       5 | unsafe |                   3,63 |                12,86 |
       5 |  safe  |                   3,18 |                11,26 |
-------------------------------------------------------------------
       6 | unsafe |                   3,87 |                13,69 |
       6 |  safe  |                   3,27 |                11,56 |
-------------------------------------------------------------------
       7 | unsafe |                   3,98 |                14,07 |
       7 |  safe  |                   3,54 |                12,53 |
-------------------------------------------------------------------
       8 | unsafe |                   3,94 |                13,95 |
       8 |  safe  |                   3,54 |                12,53 |
-------------------------------------------------------------------
       9 | unsafe |                   3,60 |                12,72 |
       9 |  safe  |                   3,20 |                11,32 |
-------------------------------------------------------------------
      10 | unsafe |                   3,92 |                13,85 |
      10 |  safe  |                   3,35 |                11,85 |
-------------------------------------------------------------------
      11 | unsafe |                   3,89 |                13,76 |
      11 |  safe  |                   3,52 |                12,47 |
-------------------------------------------------------------------
      12 | unsafe |                   4,00 |                14,17 |
      12 |  safe  |                   3,55 |                12,55 |
-------------------------------------------------------------------
      13 | unsafe |                   4,00 |                14,17 |
      13 |  safe  |                   3,53 |                12,50 |
-------------------------------------------------------------------
      14 | unsafe |                   4,00 |                14,15 |
      14 |  safe  |                   3,55 |                12,56 |
-------------------------------------------------------------------
Код:
Core i5 2300
-------------------------------------------------------------------
threads |  mode  | normalized performance | absolute performance |
-------------------------------------------------------------------
       1 | unsafe |                   1,00 |                 3,92 |
       1 |  safe  |                   1,22 |                 4,77 |
-------------------------------------------------------------------
       2 | unsafe |                   2,00 |                 7,85 |
       2 |  safe  |                   2,38 |                 9,36 |
-------------------------------------------------------------------
       3 | unsafe |                   2,97 |                11,65 |
       3 |  safe  |                   3,55 |                13,95 |
-------------------------------------------------------------------
       4 | unsafe |                   3,78 |                14,82 |
       4 |  safe  |                   4,59 |                18,02 |
-------------------------------------------------------------------
       5 | unsafe |                   3,26 |                12,81 |
       5 |  safe  |                   3,88 |                15,21 |
-------------------------------------------------------------------
       6 | unsafe |                   3,73 |                14,65 |
       6 |  safe  |                   4,46 |                17,52 |
-------------------------------------------------------------------
       7 | unsafe |                   3,75 |                14,72 |
       7 |  safe  |                   4,33 |                16,97 |
-------------------------------------------------------------------
       8 | unsafe |                   3,66 |                14,35 |
       8 |  safe  |                   4,58 |                17,97 |
-------------------------------------------------------------------
       9 | unsafe |                   3,66 |                14,34 |
       9 |  safe  |                   4,38 |                17,20 |
-------------------------------------------------------------------
      10 | unsafe |                   3,71 |                14,54 |
      10 |  safe  |                   4,49 |                17,63 |
-------------------------------------------------------------------
      11 | unsafe |                   3,80 |                14,92 |
      11 |  safe  |                   4,58 |                17,96 |
-------------------------------------------------------------------


За абсолютную единицу ансэйфной производительности принято ядро процессора Athlon 64 X2 4200+.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Среда, 19 Октябрь, 2011 19:39 

Зарегистрирован: Суббота, 07 Март, 2009 15:39
Сообщения: 3261
Откуда: Астрахань
Возможно, дело в оптимизациях по умолчанию. ИМХО unsafe-код просто не оптимизируется. В то время как safe-код может в некоторых местах оптимизирован по умолчанию.
Ы?
ПыСы. У меня вот получилось, что g++ оптимизирует лучше, чем компилятор c++ в 2010-й студии. Тоже не совсем понятно, почему. Но одна и та же программа, откомпилированная там и там, работает с разной скоростью на одном и том же компе при одинаковых условиях.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Суббота, 22 Октябрь, 2011 15:09 

Зарегистрирован: Понедельник, 30 Июль, 2007 10:53
Сообщения: 1538
Откуда: Беларусь, Минск
Цитата:
Код:
int* a = stackalloc int[n];
А факт размещения на стеке не может быть причиной?

И размер инта: он остался прежним, но выравнивается под 64 бита?


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Понедельник, 24 Октябрь, 2011 00:28 
Аватара пользователя

Зарегистрирован: Пятница, 25 Ноябрь, 2005 18:55
Сообщения: 2272
Откуда: Россия, Нижний Новгород
Если это вы мне вопросы задаёте, то напрасно. Я не знаю.

Я тут ещё другую штуку откопал. Процедура в которой осуществляется три вложенных цикла (по x, y, z) над трёхмерными массивами f[x,y,z] (сложение, умножение элементов массива (фактически, решение в лоб 3х-мерного уравнения Даламбера)) на том компьютере (сэнди бридж i5 2300, Windows 7, 64 bit) работает В ВОСЕМЬ РАЗ БЫСТРЕЕ чем на Athlon 64 X2 4200+ под Windows XP 32 bit или на Core i7 950 Linux, Mono 2.6.x 32 bit.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Понедельник, 24 Октябрь, 2011 05:15 
Аватара пользователя

Зарегистрирован: Суббота, 27 Февраль, 2010 23:34
Сообщения: 746
Сергей Губанов писал(а):
Если это вы мне вопросы задаёте, то напрасно. Я не знаю.

Я тут ещё другую штуку откопал. Процедура в которой осуществляется три вложенных цикла (по x, y, z) над трёхмерными массивами f[x,y,z] (сложение, умножение элементов массива (фактически, решение в лоб 3х-мерного уравнения Даламбера)) на том компьютере (сэнди бридж i5 2300, Windows 7, 64 bit) работает В ВОСЕМЬ РАЗ БЫСТРЕЕ чем на Athlon 64 X2 4200+ под Windows XP 32 bit или на Core i7 950 Linux, Mono 2.6.x 32 bit.
Речь идёт о целочисленной арифметике или об обработке вещественных чисел?..
Вообще надо учитывать, что в 64-разрядном режиме используются все возможности архитектуры AMD64, а это не только повышение разрядности основных регистров, но и дополнительные 8 GPRs, 16 регистров по 256 разрядов (YMM)... При этом AMD отмечает, что "Maximum floating-point performance can be achieved using the 256-bit media instructions." (стр. 6).
То есть, IMHO, дело не в компиляторе, а в 64-разрядной ОС, которая позволяет более полно задействовать возможности процессора.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: Понедельник, 24 Октябрь, 2011 12:35 
Аватара пользователя

Зарегистрирован: Пятница, 25 Ноябрь, 2005 18:55
Сообщения: 2272
Откуда: Россия, Нижний Новгород
alexus писал(а):
То есть, IMHO, дело не в компиляторе, а в 64-разрядной ОС, которая позволяет более полно задействовать возможности процессора.
Видимо так оно и есть.

Вот тот цикл с вещественными числами:
Код:
for (int x = 1; x < L - 1; x++)
{
   for (int y = 1; y < L - 1; y++)
   {
      for (int z = 1; z < L - 1; z++)
      {
         a[x, y, z] = coeff1 * b[x, y, z] - c[x, y, z] + coeff2 * (b[x - 1, y, z] + b[x + 1, y, z] + b[x, y - 1, z] + b[x, y + 1, z] + b[x, y, z - 1] + b[x, y, z + 1]);
      }
   }
}
Под 64 разрядным дотнетом версии 3.5 работает в 8.2 раза быстрее на i5 2300 по сравнению с Athlon 64 X2 4200+ под 32 разрядным дотнетом. Под версией дотнета 4.0 ещё чуть-чуть ускоряется до 8.4 раз.

---------------------

Ещё померил скорость вычисления синусов. Под версией дотнета 3.5 ускорения нет (хотя частоты у процессоров разные 2.8 ГГц у i5 2300 и 2.21 ГГц у Athlon 64 X2 4200+). Под версией дотнета 4.0 получается ускорение на 20% (хотя частота больше на 26%). То есть АМД-шный Athlon синусы вычисляет быстрее чем интеловский сэнди бридж работающий на более высокой частоте.

Если кому-то надо быстро синусы вычислять, то для этого достаточно использовать "допотопный" дешёвый Athlon чем дорогой современный интеловский процессор.


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 7 ] 

Часовой пояс: UTC + 3 часа


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 8


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Вся информация, размещаемая участниками на конференции (тексты сообщений, вложения и пр.) © 2005-2024, участники конференции «OberonCore», если специально не оговорено иное.
Администрация не несет ответственности за мнения, стиль и достоверность высказываний участников, равно как и за безопасность материалов, предоставляемых участниками во вложениях.
Без разрешения участников и ссылки на конференцию «OberonCore» любое воспроизведение и/или копирование высказываний полностью и/или по частям запрещено.
Powered by phpBB® Forum Software © phpBB Group
Русская поддержка phpBB