1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84
| #include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <chrono>
#include <random>
// Version pointeur template
template<typename T, typename I, I (T::*F)() const>
struct mem_fun_comp_ {
bool operator () (const T& t1, const T& t2) const {
return (t1.*F)() < (t2.*F)();
}
};
template<typename T, typename I>
T mem_fun_owner(I (T::*f)() const) { return std::declval<T>(); }
template<typename T, typename I>
I mem_fun_return_type(I (T::*f)() const) { return std::declval<I>(); }
#define mem_fun_comp(f) mem_fun_comp_<decltype(mem_fun_owner(f)), decltype(mem_fun_return_type(f)), f>
// Version pointeur membre
template<typename T, typename I>
struct mem_fun_comp_koala {
using F = I (T::*)() const;
const F func;
mem_fun_comp_koala(F f) : func(f) {}
bool operator () (const T& t1, const T& t2) const {
return (t1.*func)() < (t2.*func)();
}
};
// Donnée à trier
struct test {
std::size_t id_;
std::size_t id() const { return id_; }
};
int main(int argc, char* argv[]) {
std::vector<test> ov;
// On génère un vecteur avec 1e6 valeurs aléatoires
std::default_random_engine gen;
std::uniform_int_distribution<std::size_t> distrib;
const std::size_t num = 1000000;
for (std::size_t i = 0; i < num; ++i) {
ov.push_back({distrib(gen)});
}
// On trie plusieurs fois ce même vecteur...
// ... avec le pointeur template
for (std::size_t i = 0; i < 5; ++i) {
auto start = std::chrono::high_resolution_clock::now();
auto v = ov;
std::sort(v.begin(), v.end(), mem_fun_comp(&test::id)());
auto end = std::chrono::high_resolution_clock::now();
auto elapsed = end - start;
std::cout << elapsed.count() << std::endl;
}
std::cout << std::endl;
// ... avec le pointeur membre
for (std::size_t i = 0; i < 5; ++i) {
auto start = std::chrono::high_resolution_clock::now();
auto v = ov;
std::sort(v.begin(), v.end(), mem_fun_comp_koala<test, std::size_t>(&test::id));
auto end = std::chrono::high_resolution_clock::now();
auto elapsed = end - start;
std::cout << elapsed.count() << std::endl;
}
return 0;
} |
Partager