Kod:
// ConsoleApplication4.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include <algorithm>
#include <ctime>
#include <iostream>
const int ITERATIONS = 100000;
void test(const char *desc, int *data, unsigned arraySize) {
// Test
clock_t start = clock();
long long sum = 0;
for (unsigned i = 0; i < ITERATIONS; ++i)
{
// Primary loop
for (unsigned c = 0; c < arraySize; ++c)
{
if (data[c] >= 128)
sum += data[c];
}
}
double elapsedTime = static_cast<double>(clock() - start) / CLOCKS_PER_SEC;
std::cout << desc << ": " << elapsedTime << std::endl;
std::cout << "sum = " << sum << std::endl;
}
int main()
{
// Generate data (f = filtered)
const unsigned arraySize = 32768;
unsigned fArraySize = 0;
int data[arraySize];
int fData[arraySize];
for (unsigned c = 0; c < arraySize; ++c)
data[c] = std::rand() % 256;
for (int i = 0; i < arraySize; i++)
if (data[i] >= 128)
fData[fArraySize++] = data[i];
test("filtered", fData, fArraySize);
test("unsorted", data, arraySize);
std::sort(data, data + arraySize);
test("sorted", data, arraySize);
return 0;
}
Kompilator: Microsoft Visual Studio 2017.
Processor: AMD Ryzen 5 1600
Testresultat med optimering avstängd (/Od):
filtered: 4.726
sum = 312275400000
unsorted: 24.831
sum = 312275400000
sorted: 8.992
sum = 312275400000
Testresultat med optimering på (/O2):
filtered: 0.826
sum = 312275400000
unsorted: 1.027
sum = 312275400000
sorted: 1.021
sum = 312275400000
Min slutats är att "sortera arrayen" inte är en generellt bra lösning på den här typen av problem. Däremot är det bra att fundera på hur man lagrar och itererar över sin data.
Och att slå på kompilatoroptimeringar. Och att moderna kompilatorer/CPU:er är rätt smarta.
Kan man stänga av processorns branch prediction med instruktioner i kompilatorn verkligen?