2017-01-04 9 views
0

Что-то вроде следующего:Являются ли компиляторы в целом способными конденсировать несколько непрерывных копий памяти в одну операцию?

struct Vec2 
{ 
    int x, y; 
}; 

struct Bounds 
{ 
    int left, top, right, bottom; 
}; 

int main() 
{ 
    Vec2 topLeft = {5, 5}; 
    Vec2 bottomRight = { 10, 10 }; 
    Bounds bounds; 
//___Here is copy operation 
//___Note they're not in contiguous order, harder for the compiler? 
    bounds.left = topLeft.x; 
    bounds.bottom = bottomRight.y; 
    bounds.top = topLeft.y; 
    bounds.right = bottomRight.x; 
} 

Эти четыре задания можно было бы сделать так:

memcpy(&bounds, &topLeft, sizeof(Vec2)); 
memcpy(&bounds.right, &bottomRight, sizeof(Vec2)); 

Я интересно, две вещи:

  1. компиляторы обычно способны оптимизировать в сюда?
  2. Имеются ли четыре экземпляра int так же, как две копии внутренней пары, поскольку память для копирования O (n)?

Я получил следующую разборку результатов для четырех копий:

bounds.left = topLeft.x; 
00007FF642291034 mov   dword ptr [bounds],5 
bounds.bottom = bottomRight.y; 
00007FF64229103C mov   dword ptr [rsp+2Ch],0Ah 
bounds.top = topLeft.y; 
00007FF642291044 mov   dword ptr [rsp+24h],5 
bounds.right = bottomRight.x; 
00007FF64229104C mov   dword ptr [rsp+28h],0Ah 

и непоследовательно, два memcpys различных инструкций для первого и второго, я не понимаю этого:

memcpy(&bounds, &topLeft, sizeof(Vec2)); 
00007FF64229105E mov   rbx,qword ptr [topLeft] // This is only one instruction 
memcpy(&bounds.right, &bottomRight, sizeof(Vec2)); 
00007FF642291063 mov   rdi,qword ptr [bottomRight] // Compared to 6? 
00007FF642291068 mov   qword ptr [bounds],rbx 
00007FF64229106D mov   qword ptr [rsp+28h],rdi 
00007FF642291072 jmp   main+7Eh (07FF64229107Eh) 
00007FF642291074 mov   rdi,qword ptr [rsp+28h] 
00007FF642291079 mov   rbx,qword ptr [bounds] 
+0

«компилятор» не является ни одной сущностью. На нескольких платформах существует несколько компиляторов с несколькими версиями. Кажется маловероятным, что кто-нибудь сможет ответить на ваш слишком широкий вопрос любыми полномочиями. Вы должны переформулировать свой вопрос как конкретную ответственную сущность, описывающую реальную количественную проблему, которую вы пытаетесь решить. – xaxxon

ответ

1

Любые современные потоки поддержки компилятора должны учитывать зависимости команд и переупорядочение. Используя эту технологию, она быстро обнаруживает, что в наборе инструкций нет зависимостей, что означает, что они могут быть переупорядочены в линейном порядке памяти, а затем объединены.

Не важно, что это имеет значение; кеш процессора будет просто загружать всю строку кэша при первом доступе и очистить всю строку кэша в какой-то более поздней точке. Эти операции требуют времени, а не сами операции ЦП.