Pagini recente » Cod sursa (job #495316) | Cod sursa (job #2427383) | Cod sursa (job #1659978) | Cod sursa (job #3168996) | Cod sursa (job #3240371)
#include<iostream>
#include<vector>
#include<algorithm>
std::vector<std::vector<std::pair<int, int> > > heaps;
std::vector<std::pair<int, int> > coord;
void init(int N)
{
heaps.resize(N);
}
void push_up(int i, int j)
{
std::vector<std::pair<int, int> >& heap=heaps[i];
int p;
while(j)
{
p=(j-1)/2;
if(heap[j].first<heap[p].first)
{
std::swap(heap[j], heap[p]);
std::swap(coord[heap[j].second].second, coord[heap[p].second].second);
j=p;
}
else
break;
}
}
void add(int i, int x)
{
int j=(int)heaps[i].size();
heaps[i].emplace_back(x, (int)coord.size());
coord.emplace_back(i, j);
push_up(i, j);
}
void push_down(int i, int j)
{
std::vector<std::pair<int, int> >& heap=heaps[i];
int p, s0, s1, N=(int)heap.size();
for(p=j;;)
{
s0=(p<<1)|1;
s1=s0+1;
if(s0>=N)
break;
if(s1<N)
{
if(heap[s1].first<heap[s0].first)
{
if(heap[s1].first<heap[p].first)
{
std::swap(heap[s1], heap[p]);
std::swap(coord[heap[s1].second].second, coord[heap[p].second].second);
p=s1;
}
else
break;
}
else if(heap[s0].first<heap[p].first)
{
std::swap(heap[s0], heap[p]);
std::swap(coord[heap[s0].second].second, coord[heap[p].second].second);
p=s0;
}
else
break;
}
else if(heap[s0].first<heap[p].first)
{
std::swap(heap[s0], heap[p]);
std::swap(coord[heap[s0].second].second, coord[heap[p].second].second);
p=s0;
}
else
break;
}
}
int get_min(int i)
{
int x=heaps[i][0].first;
heaps[i][0]=heaps[i].back();
coord[heaps[i][0].second].second=0;
heaps[i].pop_back();
push_down(i, 0);
return x;
}
void decrease_key(int i, int x)
{
int j=coord[i].second;
i=coord[i].first;
heaps[i][j].first-=x;
push_up(i, j);
}
void merge_sets(int i, int j)
{
int k, N=(int)heaps[i].size(), M=(int)heaps[j].size();
for(k=0;k<M;++k)
{
heaps[i].emplace_back(heaps[j][k]);
coord[heaps[j][k].second].first=i;
coord[heaps[j][k].second].second=N+k;
}
heaps[j].clear();
for(j=(N+M-2)/2;j>-1;--j)
push_down(i, j);
}
int main()
{
freopen("mergeheap.in", "r", stdin);
freopen("mergeheap.out", "w", stdout);
//std::ios_base::sync_with_stdio(false);
//std::cin.tie(0);
int N, _, op, i, j, x;
std::cin>>N>>_;
init(N);
do
{
std::cin>>op>>i;
--i;
switch(op)
{
case 1:
std::cin>>x;
add(i, x);
break;
case 2:
std::cout<<get_min(i)<<'\n';
break;
/*case 3:
std::cin>>x;
decrease_key(i, x);
break;*/
case 3:
std::cin>>j;
merge_sets(i, j);
break;
}
}while(_-=1);
return 0;
}