Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <iostream>
- #include <vector>
- #include <deque>
- using namespace std;
- enum heap_type
- {
- heap_max = 0,
- heap_min = 1
- };
- class Heap
- {
- std::vector<int> h;
- std::vector<int> ID_to_HeapIdx;
- int heap_size;
- int curr_ID;
- public:
- Heap();
- void siftup(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID);
- void siftdown(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID);
- void add(int sort_type, int vertex, int ID, std::vector<int>& HeapIdx_to_ID);
- void delete_vertex(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID);
- bool isempty();
- void out();
- int get_root();
- };
- Heap::Heap()
- {
- std::vector<int> h;
- heap_size = 0;
- std::vector<int> ID_to_HeapIdx;
- }
- int Heap::get_root()
- {
- if (heap_size > 0)
- return h[0];
- return -1;
- }
- bool Heap::isempty()
- {
- if (heap_size == 0)
- return true;
- return false;
- }
- void Heap::siftup(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID)
- {
- int curr, parent, tmp;
- curr = heap_size - 1;
- parent = (curr - 1);
- for (int i = 0; i < HeapIdx_to_ID.size(); i++)
- for (int i = 0; i < ID_to_HeapIdx.size(); i++)
- while (parent >= 0 && curr > 0)
- {
- if (sort_type == heap_max & h[parent] < h[curr])
- {
- int buff = h[curr];
- h[curr] = h[parent];
- h[parent] = buff;
- tmp = HeapIdx_to_ID[parent];
- HeapIdx_to_ID[parent] = HeapIdx_to_ID[curr];
- HeapIdx_to_ID[curr] = tmp;
- tmp = ID_to_HeapIdx[HeapIdx_to_ID[parent]];
- ID_to_HeapIdx[HeapIdx_to_ID[parent]] = ID_to_HeapIdx[HeapIdx_to_ID[curr]];
- ID_to_HeapIdx[HeapIdx_to_ID[curr]] = tmp;
- }
- if (sort_type == heap_min & h[parent] > h[curr])
- {
- int buff = h[curr];
- h[curr] = h[parent];
- h[parent] = buff;
- tmp = HeapIdx_to_ID[parent];
- HeapIdx_to_ID[parent] = HeapIdx_to_ID[curr];
- HeapIdx_to_ID[curr] = tmp;
- tmp = ID_to_HeapIdx[HeapIdx_to_ID[parent]];
- ID_to_HeapIdx[HeapIdx_to_ID[parent]] = ID_to_HeapIdx[HeapIdx_to_ID[curr]];
- ID_to_HeapIdx[HeapIdx_to_ID[curr]] = tmp;
- }
- curr = parent;
- parent = (curr - 1);
- }
- }
- void Heap::add(int sort_type, int vertex, int ID, std::vector<int>& HeapIdx_to_ID)
- {
- h.push_back(vertex);
- ID_to_HeapIdx.push_back(heap_size);
- HeapIdx_to_ID.push_back(ID);
- cout << "Только что добавили элемент в конец кучи" << endl;
- if (sort_type == heap_max)
- cout << "ID_to_Heap1Idx[ID]= " ;
- else
- cout << "ID_to_Heap2Idx[ID]= " ;
- for (int j=0;j < ID_to_HeapIdx.size(); j++)
- cout << ID_to_HeapIdx[j] << " ";
- cout << endl;
- cout << endl;
- if (sort_type == heap_max)
- cout << "HeapIdx1_to_ID[ID]= " ;
- else
- cout << "HeapIdx2_to_ID[ID]= " ;
- for (int j=0;j < HeapIdx_to_ID.size(); j++)
- cout << HeapIdx_to_ID[j] << " ";
- cout << endl;
- cout << endl;
- heap_size++;
- siftup(sort_type, ID, HeapIdx_to_ID);
- cout << "После сифтапа" << endl;
- cout << "Только что добавили элемент в конец кучи" << endl;
- if (sort_type == heap_max)
- cout << "ID_to_Heap1Idx[ID]= " ;
- else
- cout << "ID_to_Heap2Idx[ID]= " ;
- for (int j=0;j < ID_to_HeapIdx.size(); j++)
- cout << ID_to_HeapIdx[j] << " ";
- cout << endl;
- cout << endl;
- if (sort_type == heap_max)
- cout << "HeapIdx1_to_ID[ID]= " ;
- else
- cout << "HeapIdx2_to_ID[ID]= " ;
- for (int j=0;j < HeapIdx_to_ID.size(); j++)
- cout << HeapIdx_to_ID[j] << " ";
- cout << endl;
- cout << endl;
- }
- void Heap::siftdown(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID)
- {
- int parent, max_child, min_child, tmp, buff;
- int curr = ID_to_HeapIdx[ID];
- int child_l = 2 * curr + 1;
- int child_r = 2 * curr + 2;
- if (h[child_r] < h[child_l])
- {
- max_child = child_l;
- min_child = child_r;
- }
- else
- {
- max_child = child_r;
- min_child = child_l;
- }
- while (child_l < heap_size)
- {
- if (sort_type == heap_max)
- {
- if (child_l == heap_size - 1)
- max_child = child_l;
- else if (h[child_r] < h[child_l])
- max_child = child_l;
- else
- max_child = child_r;
- }
- if (sort_type == heap_min)
- {
- if (child_l == heap_size - 1)
- min_child = child_l;
- else if (h[child_r] < h[child_l])
- min_child = child_r;
- else
- min_child = child_l;
- }
- if (sort_type == heap_max & h[curr] < h[max_child])
- {
- buff = h[curr];
- h[curr] = h[max_child];
- h[max_child] = buff;
- tmp = HeapIdx_to_ID[max_child];
- HeapIdx_to_ID[max_child] = HeapIdx_to_ID[curr];
- HeapIdx_to_ID[curr] = tmp;
- tmp = ID_to_HeapIdx[HeapIdx_to_ID[max_child]];
- ID_to_HeapIdx[HeapIdx_to_ID[max_child]] = ID_to_HeapIdx[HeapIdx_to_ID[curr]];
- ID_to_HeapIdx[HeapIdx_to_ID[curr]] = tmp;
- }
- if (sort_type == heap_min & h[curr] > h[max_child])
- {
- buff = h[curr];
- h[curr] = h[max_child];
- h[max_child] = buff;
- tmp = HeapIdx_to_ID[max_child];
- HeapIdx_to_ID[max_child] = HeapIdx_to_ID[curr];
- HeapIdx_to_ID[curr] = tmp;
- tmp = ID_to_HeapIdx[HeapIdx_to_ID[max_child]];
- ID_to_HeapIdx[HeapIdx_to_ID[max_child]] = ID_to_HeapIdx[HeapIdx_to_ID[curr]];
- ID_to_HeapIdx[HeapIdx_to_ID[curr]] = tmp;
- }
- curr = max_child;
- child_l = 2 * curr + 1;
- child_r = 2 * curr + 2;
- }
- }
- void Heap::delete_vertex(int sort_type, int ID, std::vector<int>& HeapIdx_to_ID)
- {
- int pos = ID_to_HeapIdx[ID];
- cout << "поступил запрос на удаление по ID= " << ID << "pos in heap = " << pos << endl;
- cout << "h[pos]" << h[pos] << endl;
- cout << "DO" << endl;
- if (sort_type == heap_max)
- cout << "ID_to_Heap1Idx[ID]= " ;
- else
- cout << "ID_to_Heap2Idx[ID]= " ;
- for (int j=0;j < ID_to_HeapIdx.size(); j++)
- cout << ID_to_HeapIdx[j] << " ";
- cout << endl;
- cout << endl;
- if (sort_type == heap_max)
- cout << "HeapIdx1_to_ID[ID]= " ;
- else
- cout << "HeapIdx2_to_ID[ID]= " ;
- for (int j=0;j < HeapIdx_to_ID.size(); j++)
- cout << HeapIdx_to_ID[j] << " ";
- cout << endl;
- cout << endl;
- h[pos] = h[heap_size - 1];
- h.pop_back();
- heap_size--;
- //ID_to_HeapIdx[HeapIdx_to_ID[pos]] = -100; //Беру айди элемента pos и теперь Id[id] = -100;
- //cout << "ID элемента которые лежит на pos " << HeapIdx_to_ID[pos] << " " << HeapIdx_to_ID[heap_size] << endl;
- HeapIdx_to_ID[pos] = HeapIdx_to_ID[heap_size];
- HeapIdx_to_ID[heap_size] = -100;
- //cout << "ID элемента которые лежит на pos " << HeapIdx_to_ID[pos] << " " << HeapIdx_to_ID[heap_size] << endl;
- //cout << "pos " << pos << heap_size << endl;
- ID_to_HeapIdx[HeapIdx_to_ID[pos]] = pos; //Дают айди послед эл, а он уже на Pos
- siftdown(sort_type, ID, HeapIdx_to_ID);
- cout << "ID_to_HeapIdx[HeapIdx_to_ID[pos]] = " << ID_to_HeapIdx[HeapIdx_to_ID[pos]] << endl;
- cout << "POSLE" << endl;
- if (sort_type == heap_max)
- cout << "ID_to_Heap1Idx[ID]= " ;
- else
- cout << "ID_to_Heap2Idx[ID]= " ;
- for (int j=0;j < ID_to_HeapIdx.size(); j++)
- cout << ID_to_HeapIdx[j] << " ";
- cout << endl;
- cout << endl;
- if (sort_type == heap_max)
- cout << "HeapIdx1_to_ID[ID]= " ;
- else
- cout << "HeapIdx2_to_ID[ID]= " ;
- for (int j=0;j < HeapIdx_to_ID.size(); j++)
- cout << HeapIdx_to_ID[j] << " ";
- cout << endl;
- cout << endl;
- }
- void Heap::out(void)
- {
- for (int i = 0; i < heap_size; i++)
- {
- cout << h[i] << " ";
- }
- cout << endl;
- }
- int main()
- {
- Heap heap1;
- Heap heap2;
- std::vector<int> HeapIdx1_to_ID;
- std::vector<int> HeapIdx2_to_ID;
- char c;
- int count = 1;
- int ID1 = -1;
- int ID2 = -1;
- deque<int> deq1;
- deque<int> deq2;
- int N, M, K, ID, root1_ID, root2_ID;
- N = 4;
- M = 6;
- K = 1;
- int ID1toID2[N];
- int ID2toID1[N];
- int R = 0, L = 0;
- //int a[N] = { 4, 2, 1, 3, 6, 5, 7 };
- int a[N] = { 1,2,3,4};
- ID1++;
- heap1.add(heap_max, a[0], ID1, HeapIdx1_to_ID);
- deq1.push_back(ID1);
- cout << "До цикла heap1 :";
- heap1.out();
- cout << "До цикла heap2 :";
- heap2.out();
- for (int i = 1; i < M; ++i)
- {
- cin >> c;
- if (c == 'R')
- {
- count++;
- R++;
- cout << "----------------" << endl;
- cout << "R; R = " << R << " count =" << count << endl;
- if (count < K)
- {
- cout << "count < K, просто добавляю в кучу" << endl;
- ID1++;
- heap1.add(heap_max, a[R], ID1, HeapIdx1_to_ID);
- deq1.push_back(ID1);
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- cout << "deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << "answer: " << "-1" << endl;
- }
- if (count == K)
- {
- cout << "count == K, просто добавляю в кучу" << endl;
- ID1++;
- heap1.add(heap_max, a[R], ID1, HeapIdx1_to_ID);
- deq1.push_back(ID1);
- cout << "deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << "answer: " << heap1.get_root() << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- if (count > K)
- {
- cout << "count > K, Появились лишние - их во вторую кучу (если больше корня, иначе в 1 а корень во вторую)" << endl;
- if (a[R] > heap1.get_root())
- {
- cout << "a[R] больше корня - во вторую кучу просто" << endl;
- ID2++;
- heap2.add(heap_min, a[R], ID2, HeapIdx2_to_ID);
- deq2.push_back(ID2);
- cout << "answer: " << heap1.get_root() << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- else
- {
- cout << "a[R] < корня, корень стал уже к+1 и его во вторую надо " << endl;
- cout << endl;
- root1_ID = HeapIdx1_to_ID[0];
- int root1 = heap1.get_root(); //Запоминаю вершину до удаления
- heap1.delete_vertex(heap_max, root1_ID, HeapIdx1_to_ID);
- cout << "do0 deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- ID1++;
- heap1.add(heap_max, a[R], ID1, HeapIdx1_to_ID);
- deq1.push_back(ID1);
- ID2++;
- heap2.add(heap_min, root1, ID2, HeapIdx2_to_ID);
- deq2.push_back(ID2);
- cout << "do deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << endl;
- deq1[root1_ID] = -ID2-1; //!!!!! Означает что лежит во второй куче на ID2
- cout << "posle deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << endl;
- ID1toID2[root1_ID] = ID2;
- ID2toID1[ID2] = root1_ID;
- cout << "answer: " << heap1.get_root() << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- }
- }
- else
- {
- L++;
- count--;
- cout << "----------------" << endl;
- cout << "L,count = " << L << " " << count << endl;
- if (count < K)
- {
- cout << "count < K /Стало недостаточно, удаляем первый добавленный в 1 кучу " << endl;
- ID = deq1[0];
- if (ID < 0)
- {
- cout << "Значит элемент лежит во 2 куче и там его надо искать" << endl;
- deq1.pop_front();
- heap2.delete_vertex(heap_min, -ID, HeapIdx2_to_ID);
- cout << "answer: " << "-1" << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- else
- {
- cout << "Значит элемент лежит в 1 куче и там его надо искать" << endl;
- deq1.pop_front();
- heap1.delete_vertex(heap_max, ID, HeapIdx1_to_ID);
- cout << "answer: " << "-1" << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- }
- if (count >= K)
- {
- cout << "count >= K; В 1 куче к-1, во 2 не пусто. Надо удалить первый в 1 куче, перебросить из 2 кучи , удалить его и вывести " << endl;
- cout << "deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << endl;
- ID = deq1[0];
- cout << "ID= " << ID << endl;
- if (ID < 0)
- {
- //ID = ID1toID2;
- cout << "Тот, кого нужно удалить находится во 2 куче, удаляем его" << endl;
- cout << "TrueID= " << -ID-1 << endl;
- deq1.pop_front();
- heap2.delete_vertex(heap_min, -ID-1, HeapIdx2_to_ID);
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- cout << "Так как удаляли из 2 кучи, первая не пострадала ничего не делаем" << endl;
- cout << "answer: " << heap1.get_root() << endl;
- }
- else
- {
- cout << "Тот, кого нужно удалить находится в 1 куче, удаляем его" << endl;
- deq1.pop_front();
- heap1.delete_vertex(heap_max, ID, HeapIdx1_to_ID);
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- cout << "Так как удаляли из 1 кучи, надо перебросить" << endl;
- ID1++;
- heap1.add(heap_max, heap2.get_root(), ID1, HeapIdx1_to_ID);
- int ID_top2 = HeapIdx2_to_ID[0];
- heap2.delete_vertex(heap_min, ID_top2, HeapIdx2_to_ID);
- cout << "do deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << endl;
- deq1[ID2toID1[ID_top2]] = ID2toID1[ID_top2];
- cout << "posle deq1: ";
- for (int j=0; j < deq1.size(); ++j) {
- cout << deq1[j] << " ";
- }
- cout << endl;
- cout << "answer: " << heap1.get_root() << endl;
- cout << "heap1 :";
- heap1.out();
- cout << "heap2 :";
- heap2.out();
- }
- }
- }
- }
- return 0;
- }
Add Comment
Please, Sign In to add comment