Advertisement
Omnifarious

Benchmark - Keep only duplicated values

Oct 22nd, 2019
629
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 7.27 KB | None | 0 0
  1. // https://stackoverflow.com/questions/58498959/keep-the-duplicated-values-only-vectors-c
  2.  
  3. #include <benchmark/benchmark.h>
  4. #include <algorithm>
  5. #include <unordered_map>
  6. #include <vector>
  7. #include <random>
  8.  
  9. template <typename InputIt, typename OutputIt>
  10. OutputIt copy_duplicates(
  11.         InputIt  first,
  12.         InputIt  last,
  13.         OutputIt d_first) {
  14.     std::unordered_map<typename std::iterator_traits<InputIt>::value_type,
  15.                        std::size_t> seen;
  16.     for ( ; first != last; ++first) {
  17.         if ( 2 == ++seen[*first] ) {
  18.             // only output on the second time of seeing a value
  19.             *d_first = *first;
  20.             ++d_first;
  21.         }
  22.     }
  23.     return d_first;
  24. }
  25.  
  26. template<typename T>
  27. auto erase_unique_and_duplicates(std::vector<T>& v)
  28. {
  29.   auto first{v.begin()};
  30.   std::sort(first, v.end());
  31.   while (first != v.end())
  32.   {
  33.     auto n{std::count(first, v.end(), *first)};
  34.     if (n > 1)
  35.     {
  36.       first = v.erase(first + 1, first + n);
  37.     }
  38.     else
  39.     {
  40.       first = v.erase(first);
  41.     }
  42.   }
  43.   return v.end();
  44. }
  45.  
  46. template <typename T>
  47. void only_distinct_duplicates(::std::vector<T> &v)
  48. {
  49.     ::std::sort(v.begin(), v.end());
  50.     auto output = v.begin();
  51.     auto test = v.begin();
  52.     auto run_start = v.begin();
  53.     auto const end = v.end();
  54.     for (auto test = v.begin(); test != end; ++test) {
  55.        if (*test != *run_start) {
  56.            if ((test - run_start) > 1) {
  57.               ::std::swap(*output, *run_start);
  58.               ++output;
  59.            }
  60.            run_start = test;
  61.        }
  62.     }
  63.     if ((end - run_start) > 1) {
  64.         ::std::swap(*output, *run_start);
  65.         ++output;
  66.     }
  67.     v.erase(output, end);
  68. }
  69.  
  70.  
  71. constexpr unsigned long long seed = 500;
  72.  
  73.  
  74. ::std::vector<int>
  75. make_random_list(::std::vector<int>::size_type length,
  76.                  unsigned int load_factor = 10)
  77. {
  78.    using ::std::mt19937;
  79.    using ::std::vector;
  80.    using ::std::uniform_int_distribution;
  81.    mt19937 gen(seed);
  82.    uniform_int_distribution<> dis(0, (length + 9) / load_factor);
  83.    vector<int> output;
  84.    output.reserve(length);
  85.    while (length--) {
  86.       output.push_back(dis(gen));
  87.    }
  88.    return output;
  89. }
  90.  
  91.  
  92. static void CopyDuplicates(benchmark::State& state)
  93. {
  94.    using vecint = ::std::vector<int>;
  95.    state.PauseTiming();
  96.    vecint v = make_random_list(state.range(0));
  97.    state.ResumeTiming();
  98.    for (auto _ : state) {
  99.       std::vector<int> w;
  100.       // Make sure the variable is not optimized away by compiler
  101.       benchmark::DoNotOptimize(copy_duplicates(v.begin(), v.end(), std::back_inserter(w)));
  102.    }
  103.   state.SetComplexityN(state.range(0));
  104. }
  105. // Register the function as a benchmark
  106. BENCHMARK(CopyDuplicates)
  107. ->RangeMultiplier(2)->Range(1<<6, 1<<28)->Complexity()->Unit(benchmark::kMillisecond);
  108.  
  109. static void Erase(benchmark::State& state)
  110. {
  111.    using vecint = ::std::vector<int>;
  112.    // Code before the loop is not measured
  113.    for (auto _ : state) {
  114.       state.PauseTiming();
  115.       vecint v = make_random_list(state.range(0));
  116.       state.ResumeTiming();
  117.       benchmark::DoNotOptimize(v);
  118.       benchmark::DoNotOptimize(erase_unique_and_duplicates(v));
  119.    }
  120.   state.SetComplexityN(state.range(0));
  121. }
  122. BENCHMARK(Erase)
  123. ->RangeMultiplier(4)->Range(1<<6, 1<<20)->Complexity()->Unit(benchmark::kMillisecond);
  124.  
  125. static void Only(benchmark::State& state)
  126. {
  127.    using vecint = ::std::vector<int>;
  128.    // Code before the loop is not measured
  129.    for (auto _ : state) {
  130.       state.PauseTiming();
  131.       vecint v = make_random_list(state.range(0));
  132.       state.ResumeTiming();
  133.       benchmark::DoNotOptimize(v);
  134.       only_distinct_duplicates(v);
  135.       benchmark::DoNotOptimize(v);
  136.    }
  137.   state.SetComplexityN(state.range(0));
  138. }
  139. BENCHMARK(Only)
  140. ->RangeMultiplier(4)->Range(1<<6, 1<<28)->Complexity()->Unit(benchmark::kMillisecond);
  141.  
  142. /*
  143. 2019-10-22 12:55:21
  144. Running /tmp/the_above_benchmark
  145. Run on (8 X 3900 MHz CPU s)
  146. CPU Caches:
  147.   L1 Data 32K (x4)
  148.   L1 Instruction 32K (x4)
  149.   L2 Unified 256K (x4)
  150.   L3 Unified 8192K (x1)
  151. ----------------------------------------------------------------
  152. Benchmark                         Time           CPU Iterations
  153. ----------------------------------------------------------------
  154. CopyDuplicates/64         345022038 ms          2 ms          1
  155. CopyDuplicates/128        345022038 ms          2 ms          1
  156. CopyDuplicates/256        345022038 ms          2 ms          1
  157. CopyDuplicates/512        345022038 ms          2 ms          1
  158. CopyDuplicates/1024       345022038 ms          2 ms          1
  159. CopyDuplicates/2048       345022039 ms          2 ms          1
  160. CopyDuplicates/4096       345022039 ms          3 ms          1
  161. CopyDuplicates/8192       345022039 ms          3 ms          1
  162. CopyDuplicates/16384      345022039 ms          3 ms          1
  163. CopyDuplicates/32768      345022041 ms          4 ms          1
  164. CopyDuplicates/65536      345022043 ms          6 ms          1
  165. CopyDuplicates/131072     345022047 ms         11 ms          1
  166. CopyDuplicates/262144     345022056 ms         20 ms          1
  167. CopyDuplicates/524288     345022074 ms         38 ms          1
  168. CopyDuplicates/1048576    345022113 ms         77 ms          1
  169. CopyDuplicates/2097152    345022228 ms        192 ms          1
  170. CopyDuplicates/4194304    345022707 ms        669 ms          1
  171. CopyDuplicates/8388608    345024159 ms       2117 ms          1
  172. CopyDuplicates/16777216   345027644 ms       5593 ms          1
  173. CopyDuplicates/33554432   345035493 ms      13421 ms          1
  174. CopyDuplicates/67108864   345051995 ms      29876 ms          1
  175. CopyDuplicates/134217728  345086343 ms      64134 ms          1
  176. CopyDuplicates/268435456  345160770 ms     138364 ms          1
  177. CopyDuplicates_BigO        67984.94 NlgN      18.19 NlgN
  178. CopyDuplicates_RMS               94 %          8 %
  179. Erase/64                          0 ms          0 ms     785419
  180. Erase/256                         0 ms          0 ms     236024
  181. Erase/1024                        0 ms          0 ms      27632
  182. Erase/4096                        0 ms          0 ms       2273
  183. Erase/16384                       3 ms          3 ms        205
  184. Erase/65536                      51 ms         51 ms         14
  185. Erase/262144                    862 ms        860 ms          1
  186. Erase/1048576                 14403 ms      14365 ms          1
  187. Erase_BigO                     0.01 N^2       0.01 N^2
  188. Erase_RMS                         1 %          1 %
  189. Only/64                           0 ms          0 ms     823730
  190. Only/256                          0 ms          0 ms     310661
  191. Only/1024                         0 ms          0 ms      46385
  192. Only/4096                         0 ms          0 ms       4439
  193. Only/16384                        1 ms          1 ms        906
  194. Only/65536                        3 ms          3 ms        205
  195. Only/262144                      16 ms         16 ms         44
  196. Only/1048576                     69 ms         69 ms         10
  197. Only/4194304                    310 ms        310 ms          2
  198. Only/16777216                  1363 ms       1360 ms          1
  199. Only/67108864                  5775 ms       5760 ms          1
  200. Only/268435456                25268 ms      25205 ms          1
  201. Only_BigO                      3.36 NlgN       3.35 NlgN
  202. Only_RMS                          1 %          1 %
  203. */
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement