vadimk772336

код ревью

Nov 26th, 2021 (edited)
870
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 6.29 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <random>
  4.  
  5. const int shift = 1e9; // Сдвиг ключа на 1e9, чтобы все были неотрицательными
  6. const int p = 2e9 + 33; // Простое число, большее макс. знач ключа
  7. const int multiplier = 3; // O(n) ~ 3n
  8.  
  9. std::random_device rand_dev;
  10. std::mt19937 generator(rand_dev());
  11.  
  12. struct vertex
  13. {
  14.     bool visited = false;
  15.     std::vector<struct adj_vertex> adj_list;
  16.     int list_size = 0;
  17.     int label = 0;
  18. };
  19.  
  20. struct adj_vertex
  21. {
  22.     int idx;
  23.     int edge_value;
  24. };
  25.  
  26. class FixedSet
  27. {
  28.     int count_numbers;
  29.     int alpha_a, alpha_b, beta_a, beta_b;
  30.     std::vector<int> set;
  31.     std::vector<int> labels_array;
  32.     int labels_array_size;
  33.  
  34. public:
  35.     FixedSet();
  36.     void Initialize(const std::vector<int>& numbers);
  37.     bool Contains(int number) const;
  38.  
  39. private:
  40.     int rand_int(int min, int max);
  41.     int uni_hash(long long int a, long long int b, int m, int key) const;
  42.  
  43.     class Graph
  44.     {
  45.         struct vertex* graph;
  46.         int count_edges;
  47.         int count_vertex;
  48.  
  49.     public:
  50.         explicit Graph(int count_vertex);
  51.         void addEdge(int i, int j, int key_idx);
  52.         void DFS(int v_idx, int value, bool& flag);
  53.         bool is_correct();
  54.         int get_label(int vertex_idx);
  55.         void clear();
  56.     };
  57. };
  58.  
  59. FixedSet::Graph::Graph(int count_vertex)
  60. {
  61.     graph = new vertex[count_vertex];
  62.     this->count_edges = 0;
  63.     this->count_vertex = count_vertex;
  64. }
  65.  
  66. int FixedSet::Graph::get_label(int vertex_idx)
  67. {
  68.     return graph[vertex_idx].label;
  69. }
  70.  
  71.  
  72. void FixedSet::Graph::clear()
  73. {
  74.     for (int i = 0; i < (this->count_vertex); ++i)
  75.     {
  76.         graph[i].list_size = 0;
  77.         graph[i].label = 0;
  78.         graph[i].adj_list.clear();
  79.         graph[i].visited = false;
  80.         this->count_edges = 0;
  81.     }
  82. }
  83.  
  84. void FixedSet::Graph::addEdge(int i, int j, int key_idx)
  85. {
  86.     adj_vertex buff;
  87.     buff.idx = j;
  88.     buff.edge_value = key_idx;
  89.  
  90.     graph[i].adj_list.push_back(buff);
  91.  
  92.     buff.idx = i;
  93.     graph[j].adj_list.push_back(buff);
  94.  
  95.     graph[i].list_size++;
  96.     graph[j].list_size++;
  97.     this->count_edges++;
  98. }
  99.  
  100. void FixedSet::Graph::DFS(int v_idx, int value, bool& flag)
  101. {
  102.  
  103.     if (flag)
  104.     {
  105.         graph[v_idx].visited = true;
  106.         graph[v_idx].label = value;
  107.  
  108.         vertex u;
  109.         std::vector<struct adj_vertex> curr_list = graph[v_idx].adj_list;
  110.         int u_idx, u_value, edge_value;
  111.  
  112.         for (int i = 0; i < graph[v_idx].list_size; ++i)
  113.         {
  114.  
  115.             u_idx = curr_list[i].idx;
  116.             u = graph[u_idx];
  117.             edge_value = curr_list[i].edge_value;
  118.  
  119.             if (!(u.visited))
  120.             {
  121.                 u_value = edge_value - value;
  122.                 DFS(u_idx, u_value, flag);
  123.             }
  124.  
  125.             if (((graph[u_idx].label + graph[v_idx].label) % (this->count_edges)) != edge_value)
  126.             {
  127.                 flag = false;
  128.                 break;
  129.             }
  130.         }
  131.     }
  132. }
  133.  
  134.  
  135. bool FixedSet::Graph::is_correct()
  136. {
  137.  
  138.     bool flag = true;
  139.     for (int i = 0; i < (this->count_vertex); ++i)
  140.     {
  141.         if (!graph[i].visited)
  142.             DFS(i, 0, flag);
  143.         if (!flag)
  144.             return false;
  145.     }
  146.     return true;
  147. }
  148.  
  149. FixedSet::FixedSet()
  150. {
  151.     this->count_numbers = 0;
  152.     this->labels_array_size = 0;
  153. }
  154.  
  155. int FixedSet::rand_int(int min, int max)
  156. {
  157.     std::uniform_int_distribution<int> distr(min, max);
  158.     return distr(generator);
  159. }
  160.  
  161. int FixedSet::uni_hash(long long int a, long long int b, int m, int key) const
  162. {
  163.     return ((a * key + b) % p) % labels_array_size;
  164. }
  165.  
  166. void FixedSet::Initialize(const std::vector<int>& numbers)
  167. {
  168.     set.clear();
  169.     labels_array.clear();
  170.     this->count_numbers = 0;
  171.     this->labels_array_size = 0;
  172.  
  173.     if (!numbers.empty())
  174.     {
  175.  
  176.         int n = numbers.size();
  177.         int m = multiplier * n;
  178.  
  179.         this->count_numbers = n;
  180.         this->labels_array_size = m;
  181.  
  182.         Graph graph(m);
  183.  
  184.         for (int i = 0; i < n; ++i)
  185.             set.push_back(numbers[i] + shift);
  186.  
  187.         long long int alpha_k, beta_k;
  188.         bool flag = false;
  189.         while (!flag)
  190.         {
  191.             graph.clear();
  192.  
  193.             this->alpha_a = rand_int(1, p - 1);
  194.             this->alpha_b = rand_int(0, p - 1);
  195.             this->beta_a = rand_int(1, p - 1);
  196.             this->beta_b = rand_int(0, p - 1);
  197.  
  198.             for (int key_idx = 0; key_idx < n; ++key_idx)
  199.             {
  200.                 alpha_k = uni_hash(alpha_a, alpha_b, m, numbers[key_idx] + shift);
  201.                 beta_k = uni_hash(beta_a, beta_b, m, numbers[key_idx] + shift);
  202.                 graph.addEdge(alpha_k, beta_k, key_idx);
  203.             }
  204.  
  205.             flag = graph.is_correct();
  206.         }
  207.  
  208.         for (int i = 0; i < m; ++i)
  209.             labels_array.push_back(graph.get_label(i));
  210.     }
  211. }
  212.  
  213. bool FixedSet::Contains(int number) const
  214. {
  215.     if (this->labels_array_size == 0)
  216.         return false;
  217.  
  218.     int m = this->labels_array_size;
  219.     int n = this->count_numbers;
  220.     int hash_alpha = uni_hash(this->alpha_a, this->alpha_b, m, number + shift);
  221.     int hash_beta = uni_hash(this->beta_a, this->beta_b, m, number + shift);
  222.  
  223.     int idx = (labels_array[hash_alpha] + labels_array[hash_beta]) % n;
  224.    
  225.     return (0 <= idx && this->set[idx] == (number + shift));
  226. }
  227.  
  228. std::vector<int> ReadSequence()
  229. {
  230.     size_t size;
  231.     std::cin >> size;
  232.     std::vector<int> sequence(size);
  233.     for (auto& current : sequence)
  234.     {
  235.         std::cin >> current;
  236.     }
  237.     return sequence;
  238. }
  239.  
  240. std::vector<bool> PerformRequests(const std::vector<int>& requests, const FixedSet& set)
  241. {
  242.     std::vector<bool> request_answers;
  243.     request_answers.reserve(requests.size());
  244.     for (int request : requests)
  245.     {
  246.         request_answers.push_back(set.Contains(request));
  247.     }
  248.     return request_answers;
  249. }
  250.  
  251. void PrintRequestsResponse(const std::vector<bool>& request_answers)
  252. {
  253.     for (bool answer : request_answers)
  254.     {
  255.         std::cout << (answer ? "Yes" : "No") << "\n";
  256.     }
  257. }
  258.  
  259. int main()
  260. {
  261.  
  262.     auto numbers = ReadSequence();
  263.     auto requests = ReadSequence();
  264.     FixedSet set;
  265.     set.Initialize(numbers);
  266.     PrintRequestsResponse(PerformRequests(requests, set));
  267.  
  268.     return 0;
  269. }
  270.  
Advertisement
Add Comment
Please, Sign In to add comment