Advertisement
Galebickosikasa

Untitled

Mar 31st, 2021
46
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.73 KB | None | 0 0
  1. //#pragma GCC optimize("Ofast,no-stack-protector,unroll-loops,fast-math")
  2. //#pragma GCC target("sse,sse2,sse3,ssse3,sse4,sse4.1,sse4.2,popcnt,abm,mmx,avx")
  3.  
  4. #include <iostream>
  5. #include <vector>
  6. #include <cmath>
  7. #include <algorithm>
  8. #include <set>
  9. #include <map>
  10. #include <queue>
  11. #include <random>
  12. #include <chrono>
  13. #include <cassert>
  14. #include <sstream>
  15. #include <fstream>
  16. #include <iomanip>
  17. #include <tuple>
  18. #include <array>
  19. #include <string_view>
  20. #include <list>
  21. #include <future>
  22. #include <mutex>
  23.  
  24. #define fi first
  25. #define se second
  26. #define pb push_back
  27. #define ll long long
  28. #define ld long double
  29. #define hm unordered_map
  30. #define pii pair<int, int>
  31. #define sz(a) (int)a.size()
  32. #define all(a) a.begin(), a.end()
  33. #define cinv(v) for (auto& x: v) cin >> x
  34. #define fr(i, n) for (int i = 0; i < (n); ++i)
  35. #define fl(i, l, n) for (int i = (l); i < (n); ++i)
  36.  
  37. // #define int ll
  38.  
  39. template<typename T1, typename T2>
  40. inline bool chkmin(T1 &x, const T2 &y) {
  41. if (x > y) {
  42. x = y;
  43. return 1;
  44. }
  45. return 0;
  46. }
  47.  
  48. template<typename T1, typename T2>
  49. inline bool chkmax(T1 &x, const T2 &y) {
  50. if (x < y) {
  51. x = y;
  52. return 1;
  53. }
  54. return 0;
  55. }
  56.  
  57. using namespace std;
  58.  
  59. #ifdef LOCAL
  60. #define dbg(x) cerr << #x << " : " << x << endl
  61. #else
  62. #define dbg(x)
  63. #endif
  64.  
  65. //tg: @runningcherry
  66.  
  67. template<typename Collection>
  68. string Join(const Collection &col) {
  69. bool first = true;
  70. stringstream ss;
  71. for (const auto &x: col) {
  72. if (!first) ss << ", ";
  73. first = false;
  74. ss << x;
  75. }
  76. return ss.str();
  77. }
  78.  
  79. template<typename T1, typename T2>
  80. ostream &operator<<(ostream &out, const pair<T1, T2> &v) {
  81. return out << '{' << v.fi << ", " << v.se << '}';
  82. }
  83.  
  84. template<typename T>
  85. ostream &operator<<(ostream &out, const vector<T> &v) {
  86. return out << '[' << Join(v) << ']';
  87. }
  88.  
  89. template<typename T1, typename T2>
  90. ostream &operator<<(ostream &out, const map<T1, T2> &v) {
  91. return out << '{' << Join(v) << '}';
  92. }
  93.  
  94. template<typename T>
  95. ostream &operator<<(ostream &out, const set<T> &v) {
  96. return out << '(' << Join(v) << ')';
  97. }
  98.  
  99. template<typename T>
  100. ostream &operator<<(ostream &out, const multiset<T> &v) {
  101. return out << '(' << Join(v) << ')';
  102. }
  103.  
  104. template<typename T1, typename T2>
  105. istream &operator>>(istream &in, pair<T1, T2> &a) {
  106. return in >> a.fi >> a.se;
  107. }
  108.  
  109. const ll inf = (ll) 2e9;
  110.  
  111. const int maxn = 1e5 + 20;
  112.  
  113. #define ASSERT_EQUAL(a, b) dbg((bool)(a == b))
  114. #define ASSERT(a) dbg((bool)(a))
  115.  
  116. template <typename K, typename V>
  117. class ConcurrentMap {
  118. public:
  119. static_assert(is_integral_v<K>, "ConcurrentMap supports only integer keys");
  120.  
  121. struct Access {
  122. V& ref_to_value;
  123. };
  124.  
  125. class SynchronizedMap {
  126. public:
  127. struct gay {
  128. map <K, Access>& ref;
  129. lock_guard<mutex> guard;
  130. };
  131. gay GetAccess() {
  132. return {a, lock_guard(m)};
  133. }
  134. private:
  135. mutex m;
  136. map <K, Access> a;
  137. };
  138.  
  139. explicit ConcurrentMap(size_t bucket_count) : mod (bucket_count) {
  140. kek = vector<SynchronizedMap> (bucket_count);
  141. }
  142.  
  143. Access operator[](const K& key) {
  144. int x = key % mod;
  145. auto ptt = kek[x].GetAccess ();
  146. return ptt.ref[key];
  147. }
  148.  
  149. map<K, V> BuildOrdinaryMap() {
  150. map <K, V> res;
  151. fr (i, mod) {
  152. auto ptt = kek[i].GetAccess ().ref;
  153. for (auto& x: ptt) res[x.fi] = x.se.ref_to_value;
  154. }
  155. return res;
  156. }
  157.  
  158. private:
  159. vector<SynchronizedMap> kek;
  160. int mod;
  161. };
  162.  
  163. void RunConcurrentUpdates(
  164. ConcurrentMap<int, int>& cm, size_t thread_count, int key_count
  165. ) {
  166. auto kernel = [&cm, key_count](int seed) {
  167. vector<int> updates(key_count);
  168. iota(begin(updates), end(updates), -key_count / 2);
  169. shuffle(begin(updates), end(updates), default_random_engine(seed));
  170.  
  171. for (int i = 0; i < 2; ++i) {
  172. for (auto key : updates) {
  173. dbg (key);
  174. cm[key].ref_to_value++;
  175. }
  176. }
  177. };
  178.  
  179. vector<future<void>> futures;
  180. for (size_t i = 0; i < thread_count; ++i) {
  181. futures.push_back(async(kernel, i));
  182. }
  183. }
  184.  
  185. void TestConcurrentUpdate() {
  186. const size_t thread_count = 3;
  187. const size_t key_count = 50000;
  188.  
  189. ConcurrentMap<int, int> cm(thread_count);
  190. RunConcurrentUpdates(cm, thread_count, key_count);
  191.  
  192. const auto result = cm.BuildOrdinaryMap();
  193. ASSERT_EQUAL(result.size(), key_count);
  194. for (auto& [k, v] : result) {
  195. ASSERT_EQUAL(v, 6);
  196. // AssertEqual(v, 6, "Key = " + to_string(k));
  197. }
  198. }
  199.  
  200.  
  201. int main () {
  202. ios_base::sync_with_stdio (0);
  203. cin.tie (0);
  204.  
  205.  
  206.  
  207.  
  208. }
  209.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement