Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- //
- // main.cpp
- // HW3_E
- //
- // Created by Антон Трубаков on 04/01/2018.
- // Copyright © 2018 Антон Трубаков. All rights reserved.
- //
- #include <iostream>
- #include <string>
- #include <vector>
- #include <random>
- #include <cmath>
- #include <algorithm>
- using std::cin;
- using std::cout;
- using std::endl;
- using std::string;
- using std::vector;
- using std::swap;
- using std::sort;
- typedef long long ll;
- struct HeapElem {
- HeapElem() {};
- HeapElem(ll elem, size_t initialPos) : elem(elem), initialPos(initialPos) {};
- ll elem;
- size_t initialPos;
- };
- class Solution {
- public:
- Solution(vector<ll> arr, ll size, ll kk) : arr(arr), kk(kk) {
- HeapElem interm(-1, -1);
- smallestKNumbers.resize(kk + 1, interm);
- interm.elem = 2000000000;
- otherNumbers.resize(size, interm);
- positions.resize(size, 0);
- whichHeap.resize(size, 0);
- size_K = 0;
- size_O = 0;
- Add(smallestKNumbers, size_K, compareK, arr[0], 0);
- whichHeap[0] = 1;
- positions[0] = 0;
- }
- ll Left(size_t pos) {
- Delete(pos);
- if (size_K < kk && size_O > 0) {
- HeapElem head = otherNumbers[0];
- Delete(head.initialPos);
- whichHeap[head.initialPos] = 1;
- Add(smallestKNumbers, size_K, compareK, head.elem, head.initialPos);
- }
- if (size_K == kk) {
- return smallestKNumbers[0].elem;
- } else {
- return -1;
- }
- }
- ll Right(size_t pos) {
- whichHeap[pos] = 1;
- Add(smallestKNumbers, size_K, compareK, arr[pos], pos);
- if (size_K > kk) {
- HeapElem head = smallestKNumbers[0];
- Delete(head.initialPos);
- whichHeap[head.initialPos] = 2;
- Add(otherNumbers, size_O, compareO, head.elem, head.initialPos);
- }
- if (size_K == kk) {
- return smallestKNumbers[0].elem;
- } else {
- return -1;
- }
- }
- private:
- void Add(vector<HeapElem>& heap, ll& size,
- int (*compare)(HeapElem, HeapElem), ll elem, size_t pos) {
- HeapElem newElem(elem, pos);
- size += 1;
- heap[size - 1] = newElem;
- positions[pos] = size - 1;
- siftUp(heap, size, compare, size - 1);
- }
- void Delete(ll pos) {
- if (whichHeap[pos] == 1) {
- remove(smallestKNumbers, size_K, compareK, positions[pos]);
- } else if (whichHeap[pos] == 2) {
- remove(otherNumbers, size_O, compareO, positions[pos]);
- }
- positions[pos] = 0;
- whichHeap[pos] = 0;
- }
- void siftUp(vector<HeapElem>& heap, ll& size, int (*compare)(HeapElem, HeapElem), ll pos) {
- while (compare(heap[pos], heap[(pos - 1) / 2])) {
- smartSwap(heap, pos, (pos - 1) / 2);
- pos = (pos - 1) / 2;
- }
- }
- void siftDown(vector<HeapElem>& heap, ll& size, int (*compare)(HeapElem, HeapElem), ll pos) {
- while (2 * pos + 1 < size) {
- ll left = 2 * pos + 1;
- ll right = 2 * pos + 2;
- ll next = left;
- if (right < size and compare(heap[right], heap[left])) {
- next = right;
- }
- if (compare(heap[pos], heap[next]) || heap[pos].elem == heap[next].elem) {
- break;
- }
- smartSwap(heap, pos, next);
- pos = next;
- }
- }
- void remove(vector<HeapElem>& heap, ll& size, int (*compare)(HeapElem, HeapElem), size_t pos) {
- smartSwap(heap, pos, size - 1);
- size -= 1;
- size_t initPos = heap[pos].initialPos;
- siftDown(heap, size, compare, pos);
- siftUp(heap, size, compare, positions[initPos]);
- }
- void smartSwap(vector<HeapElem>& heap, size_t first_pos, size_t second_pos) {
- swap(whichHeap[heap[first_pos].initialPos], whichHeap[heap[second_pos].initialPos]);
- swap(positions[heap[first_pos].initialPos], positions[heap[second_pos].initialPos]);
- swap(heap[first_pos].elem, heap[second_pos].elem);
- swap(heap[first_pos].initialPos, heap[second_pos].initialPos);
- }
- static int compareK(HeapElem first, HeapElem second) {
- return first.elem > second.elem;
- }
- static int compareO(HeapElem first, HeapElem second) {
- return first.elem < second.elem;
- }
- vector<ll> arr;
- vector<HeapElem> smallestKNumbers;
- vector<HeapElem> otherNumbers;
- vector<size_t> positions;
- vector<ll> whichHeap; // 0 - no heap, 1 - smallestK, 2 - other
- ll size_K;
- ll size_O;
- ll kk;
- };
- // ll naive_answer(vector<ll> elems, size_t left, size_t right, ll kk) {
- // if (right - left + 1< kk) {
- // return -1;
- // } else {
- // sort(elems.begin() + left, elems.begin() + right + 1);
- // return elems[left + kk - 1];
- // }
- // }
- // void test() {
- // size_t amount = 100;
- // size_t opers = 198;
- // ll kk = 4;
- // vector<ll> elems(amount);
- // vector<ll> operations(opers, 0);
- // for (size_t i = 0; i < amount; ++i) {
- // elems[i] = rand() % 100000;
- // }
- // for (size_t i = 0; i < amount - 1; ++i) {
- // operations[i] = 1;
- // }
- // vector<ll> answers;
- // vector<ll> naive_answers;
- // Solution sol(elems, amount, kk);
- // ll left = 0, right = 0;
- // for (size_t i = 0; i < opers; ++i) {
- // if (operations[i] == 1) {
- // ++right;
- // answers.push_back(sol.Right(right));
- // naive_answers.push_back(naive_answer(elems, left, right, kk));
- // } else {
- // answers.push_back(sol.Left(left));
- // ++left;
- // naive_answers.push_back(naive_answer(elems, left, right, kk));
- // }
- // }
- // cout << "My answers: \n";
- // for (size_t i = 0; i < answers.size(); ++i) {
- // cout << answers[i] << " ";
- // }
- // cout << endl;
- // cout << "Naive answers: \n";
- // for (size_t i = 0; i < answers.size(); ++i) {
- // cout << naive_answers[i] << " ";
- // }
- // cout << endl;
- // for (size_t i = 0; i < answers.size(); ++i) {
- // if (naive_answers[i] != answers[i]) {
- // cout << "ERROR" << endl;
- // cout << "My answers: \n";
- // for (size_t i = 0; i < answers.size(); ++i) {
- // cout << answers[i] << " ";
- // }
- // cout << endl;
- // cout << "Naive answers: \n";
- // for (size_t i = 0; i < answers.size(); ++i) {
- // cout << naive_answers[i] << " ";
- // }
- // cout << endl;
- // cout << "Initial vector: \n";
- // for (size_t i = 0; i < amount; ++i) {
- // cout << elems[i] << " ";
- // }
- // cout << endl;
- // }
- // }
- // }
- int main(int argc, const char * argv[]) {
- size_t amount, opers;
- ll kk;
- cin >> amount >> opers >> kk;
- vector<ll> elems(amount);
- for (size_t i = 0; i < amount; ++i) {
- cin >> elems[i];
- }
- vector<ll> operations(opers);
- for (size_t i = 0; i < opers; ++i) {
- char ch;
- cin >> ch;
- if (ch == 'R') {
- operations[i] = 1;
- } else {
- operations[i] = -1;
- }
- }
- Solution sol(elems, amount, kk);
- ll left = 0, right = 0;
- // vector<ll> naive_answers;
- for (size_t i = 0; i < opers; ++i) {
- if (operations[i] == 1) {
- ++right;
- cout << sol.Right(right) << " ";
- // naive_answers.push_back(naive_answer(elems, left, right, kk));
- } else {
- cout << sol.Left(left) << " ";
- ++left;
- // naive_answers.push_back(naive_answer(elems, left, right, kk));
- }
- }
- // cout << "\nNaive answers: \n";
- // for (size_t i = 0; i < naive_answers.size(); ++i) {
- // cout << naive_answers[i] << " ";
- // }
- // cout << endl;
- // for (int i = 0; i < 10000; ++i) {
- // test();
- // }
- return 0;
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement