Sto cercando di confrontare le prestazioni di std::sort
(utilizzando std::vector
di structs) vs intel ipp
sort.std :: sort vs intel ipp sort performance. Che cosa sto facendo di sbagliato?
Sto facendo funzionare questo test su un processore Intel Xeon model name : Intel(R) Xeon(R) CPU X5670 @ 2.93GHz
sto classificare un vettore di lunghezza 20000 elementi e smistamento 200 volte. Ho provato 2 differenti di routine di ordinamento ipp
. ippsSortDescend_64f_I
e ippsSortRadixDescend_64f_I
. In tutti i casi, l'ordinamento ipp
era almeno da 5 a 10 volte più lento di std::sort
. Mi aspettavo che l'ordinamento ipp
fosse più lento per gli array più piccoli, ma in caso contrario dovrebbe essere generalmente più veloce di std::sort
. Mi sto perdendo qualcosa qui? Che cosa sto facendo di sbagliato?
std::sort
è sempre più veloce in tutti i miei casi di test.
Ecco il mio programma
#include <array>
#include <iostream>
#include <algorithm>
#include <stdlib.h>
#include <time.h>
#include <sys/time.h>
#include <sys/timeb.h>
#include <vector>
#include <chrono>
#include "ipp.h"
using namespace std;
const int SIZE = 2000000;
const int ITERS = 200;
//Chrono typedefs
typedef std::chrono::high_resolution_clock Clock;
typedef std::chrono::microseconds microseconds;
//////////////////////////////////// std ///////////////////////////////////
typedef vector<double> myList;
void initialize(myList & l, Ipp64f* ptr)
{
double randomNum;
for (int i = 0; i < SIZE; i++)
{
randomNum = 1.0 * rand()/(RAND_MAX/2) - 1;
l.push_back(randomNum);
ptr[i] = randomNum;
}
}
void test_sort()
{
array<myList, ITERS> list;
array<Ipp64f*, ITERS> ippList;
// allocate
for(int i=0; i<ITERS;i++)
{
list[i].reserve(SIZE);
ippList[i] = ippsMalloc_64f(SIZE);
}
// initialize
for(int i=0;i<ITERS;i++)
{
initialize(list[i], ippList[i]);
}
cout << "\n\nTest Case 1: std::sort\n";
cout << "========================\n";
// sort vector
Clock::time_point t0 = Clock::now();
for(int i=0; i<ITERS;i++)
{
std::sort(list[i].begin(), list[i].end());
}
Clock::time_point t1 = Clock::now();
microseconds ms = std::chrono::duration_cast<microseconds>(t1 - t0);
std::cout << ms.count() << " micros" << std::endl;
////////////////////////////////// IPP ////////////////////////////////////////
cout << "\n\nTest Case 2: ipp::sort\n";
cout << "========================\n";
// sort ipp
Clock::time_point t2 = Clock::now();
for(int i=0; i<ITERS;i++)
{
ippsSortAscend_64f_I(ippList[i], SIZE);
}
Clock::time_point t3 = Clock::now();
microseconds ms1 = std::chrono::duration_cast<microseconds>(t3 - t2);
std::cout << ms1.count() << " micros" << std::endl;
for(int i=0; i<ITERS;i++)
{
ippsFree(ippList[i]);
}
}
///////////////////////////////////////////////////////////////////////////////////////
int main()
{
srand (time(NULL));
cout << "Test for sorting an array of structures.\n" << endl;
cout << "Test case: \nSort an array of structs ("<<ITERS<<" iterations) with double of length "<<SIZE<<". \n";
IppStatus status=ippInit();
test_sort();
return 0;
}
/////////////////////////////////////////////////////////////////////////////
comando compilazione è: uscita
/share/intel/bin/icc -O2 -I$(IPPROOT)/include sorting.cpp -lrt -L$(IPPROOT)/lib/intel64 -lippi -lipps -lippvm -lippcore -std=c++0x
Programma:
Test for sorting an array of structures.
Test case:
Sort an array of structs (200 iterations) with double of length 2000000.
Test Case 1: std::sort
========================
38117024 micros
Test Case 2: ipp::sort
========================
48917686 micros
Si noti che non si esegue solo il benchmark dell'ordinamento, ma anche la randomizzazione dei vettori. Ti consiglio di misurare solo l'ordinamento effettivo, molte volte aggiungendo le ore insieme per ottenere un tempo totale, quindi mostra il tempo totale e il tempo medio. –
lo proverò ora, ma solo per il test ho provato rimuovendo le funzioni 'randomize' in modo che solo il primo ciclo abbia un vettore casuale dove altre iterazioni hanno vettori ordinati. In questo caso anche 'std :: sort' era molto più veloce di' ipp'. comunque, controllando aggiungendo ora il tempo. – Alok
@usr: il confronto non dovrebbe restituire un numero negativo o alcun numero. Dovrebbe restituire un bool. Vero se il primo argomento dovrebbe precedere il secondo e falso altrimenti. –