Pagini recente » Cod sursa (job #2764555) | Cod sursa (job #1053793) | Cod sursa (job #1611778) | Cod sursa (job #550805) | Cod sursa (job #2728011)
#include <iostream>
#include <fstream>
using namespace std;
ifstream fin("deque.in");
ofstream fout("deque.out");
int main()
{
int n, k;
long long s=0;
fin>>n>>k;
int v[n], deq[5000000]={0};
for (int i = 1; i <= n; i++)
fin>>v[i];
int frontt = 1, backk = 0; // Initializare, Back < Front => deque-ul este vid
for (int i = 1; i <= n; i++)
{
// Cat timp elementul curent este mai mic decat ultimul element din deque, eliminam pozitia ultimului element din deque
while (frontt <= backk && v[i] <= v[deq[backk]])
backk--;
// Adaugam pozitia elementului curent in deque
deq[++backk] = i;
// Daca elementul minim coincide cu cel de pe pozita i-K, ii eliminam pozitia din deque, deoarece acesta nu mai conteaza pentru pasii >= i
if (deq[frontt] == i-k)
frontt++;
// Afisam minimul, acesta aflandu-se in varful deque-ului
if (i >= k)
s += v[deq[frontt]];
}
fout<<s;
fout.close();
return 0;
}
/* O solutie de complexitate O(N) foloseste o coada cu doua capete (double ended queue, deque). In aceasta structura, valorile pot fi inserate
sau eliminate atat pe la inceputul, cat si pe la sfarsitul deque-ului, toate aceste operatii avand loc in timp O(1) amortizat.
Se observa ca daca exista doua elemente Ai si Aj astfel incat Ai <= Aj si i > j, atunci Ai va fi mereu preferat pentru minim fata de Aj,
pentru secventele ce incep dupa pozitia i (inclusiv). Din acest motiv, la fiecare pas i, elementul curent Ai elimina de la finalul deque-ului
toate elementele mai mari sau egale cu el, apoi este inserat la finalul cozii. In acest fel, elementele din deque sunt mentinute in ordine crescatoare,
deci minimul se va afla la inceput. Se elimina apoi minimul de la inceputul cozii daca acesta nu mai apartine secventei curente (pozitia lui este
mai mica sau egala cu i-K). In final, se aduna minimul la solutie. */