Когда мы сравниваем программы на разных языках, а точнее исполняемые модули,
скомпилированные разными компиляторами, следует определиться,
как мы осуществляем сравнение. Как правило, все современные компиляторы создают
код в трех режимах: не оптимизированный, оптимизированный по быстроте исполнения
и оптимизированный по объему кода. В некоторых (простых) случаях вторая и третья
оптимизация дают один и тот же результата. Второй момент, который следует учитывать
это структуры программ, которые мы подвергаем оптимизации. В одних случаях может
перевешивать один компилятор, в других - другой. Будем помнить об этом в дальнейшем.
И так некоторые результаты моих исследований. Я буду пользоваться не промежуточным
ассемблерным кодом, а дизассемблером Ida Pro. В настоящее время это лучший дизассемблер.
Он работает со всеми основными исполняемыми и объектными форматами.
Так что мы легко , например, можем сравнить исполняемый код в Windows и в Linux.
И так, программа на языке pascal. Компилятор free-pascal.
- Код: Выделить всё
program Project1;
{$mode objfpc}{$H+}
var
i,s:integer;
begin
s:=0;
for i:=1 to 1024 do
begin
s:=s+i;
end;
writeln(s);
end.
Программа на C++. Компилятор Visual C++.
- Код: Выделить всё
#include <stdio.h>
int i,s;
void main()
{
s=0;
for(i=1; i<=1024; i++)
{
s=s+i;
}
printf("%d\n",s);
}
Паскаль. Без оптимизации.
- Код: Выделить всё
.text:0040137E mov ds:dword_408004, 0
.text:00401388 mov ds:dword_408000, 1
.text:00401392 dec ds:dword_408000
.text:00401398
.text:00401398 loc_401398:
.text:00401398 inc ds:dword_408000
.text:0040139E mov edx, ds:dword_408004
.text:004013A4 mov eax, ds:dword_408000
.text:004013A9 add edx, eax
.text:004013AB mov ds:dword_408004, edx
.text:004013B1 cmp ds:dword_408000, 400h
.text:004013BB jl short loc_401398
Паскаль (оптимизация o3)
- Код: Выделить всё
.text:0040137F mov ebx, 0
.text:00401384 mov edx, 1
.text:00401389 dec edx
.text:0040138A mov esi, esi
.text:0040138C
.text:0040138C loc_40138C:
.text:0040138C inc edx
.text:0040138D mov eax, edx
.text:0040138F add eax, ebx
.text:00401391 mov ebx, eax
.text:00401393 cmp edx, 400h
.text:00401399 jl short loc_40138C
Другие виды оптимизации не дают иных результатов. Слишком прост код.
C++. Без оптимизации.
- Код: Выделить всё
.text:00401003 mov dword_40301C, 0
.text:0040100D mov dword_403018, 1
.text:00401017 jmp short loc_401026
.text:00401019 loc_401019:
.text:00401019 mov eax, dword_403018
.text:0040101E add eax, 1
.text:00401021 mov dword_403018, eax
.text:00401026 loc_401026:
.text:00401026 cmp dword_403018, 400h
.text:00401030 jg short loc_401046
.text:00401032 mov ecx, dword_40301C
.text:00401038 add ecx, dword_403018
.text:0040103E mov dword_40301C, ecx
.text:00401044 jmp short loc_401019
.text:00401046 loc_401046:
С++. Оптимизация по объему кода.
- Код: Выделить всё
.text:00401000 xor eax, eax
.text:00401002 xor ecx, ecx
.text:00401004 inc eax
.text:00401005
.text:00401005 loc_401005:
.text:00401005 add ecx, eax
.text:00401007 inc eax
.text:00401008 cmp eax, 400h
.text:0040100D jle short loc_401005
С++. Оптимизация по объему кода (по сути тот же результат,
поскольку слишком простая программа).
- Код: Выделить всё
.text:00401000 xor ecx, ecx
.text:00401002 mov eax, 1
.text:00401007
.text:00401007 loc_401007:
.text:00401007 add ecx, eax
.text:00401009 inc eax
.text:0040100A cmp eax, 400h
.text:0040100F jle short loc_401007
Результат мне кажется весьма интересен. Я бы сказал счет один-один
и сейчас объясню. Не оптимизированные варианты. Паскалевский код короче.
Но есть два момента. Здесь требуется проверка, но я пока говорю по памяти.
Дело в том, что если a - адрес ячейки,
- Код: Выделить всё
inc a
, выполняется медленнее,
чем
- Код: Выделить всё
mov eax,a/add eax,1/mov a,eax
. Есть и еще один нюансик, но здесь
я помню не точно и это следует проверить. А именно, условный переход
выполняется медленнее, чем условный переход без перехода+безусловный
переход. Таким образом изначально компилятор free-pascal ориентирован
на объем, а Visual C++ на скорость.
В случае же использования оптимизированного
кода Visual C++ несколько лучше оптимизирует, чем free-pascal (см. листинги).
Это мой первый выпуск. Далее я продолжу свои исследования.
P.S.
Да, и сранение по скорости также будет, но позднее, просто и другие дела есть.