zoj 3963 Heap Partition 贪心+upper_bound()

来源:互联网 发布:枪炮与玫瑰乐队 知乎 编辑:程序博客网 时间:2024/05/22 06:50

题目链接

题意:

构造尽可能少的一种结构,父节点的值小于等于子节点,而且子节点在序列中出现在父节点

后面。而且每个父节点多有两个子节点。

思路:

 这个题就是贪心来做就好,对于新来的一个点,我们看看在前面能否找到比该点值小的,如果

有,就利用贪心的思想,找前比他小的当中最大的那一个来,如果找不到的话就必须要新增加

一个堆了.另外需要注意的是,由于一个父节点最多有两个子节点,所以我们要开一个数组记录

该父节点的子节点数,当等于两个时候,就将其从set中删除.至于找到前面的当中最小的当中

最大的那个,我们这里可以用到upper_bound(),找到其前面当中大于该数的第一个数.那么往

前一个就是最小的当中最大的那个了.注意我们找到返回的是地址)

剩下的就是一些细节就不多说了....

#include<bits/stdc++.h>#define Ri(a) scanf("%d", &a)#define Rl(a) scanf("%lld", &a)#define Rf(a) scanf("%lf", &a)#define Rs(a) scanf("%s", a)#define Pi(a) printf("%d\n", (a))#define Pf(a) printf("%lf\n", (a))#define Pl(a) printf("%lld\n", (a))#define Ps(a) printf("%s\n", (a))#define W(a) while(a--)#define CLR(a, b) memset(a, (b), sizeof(a))#define MOD 100000007#define inf 0x3f3f3f3f#define exp 0.00000001#define  pii  pair<int, int>#define  mp   make_pair#define  pb   push_backusing namespace std;typedef long long ll;const int maxn=1e5+10;int num[maxn],dgree[maxn];vector<int>vt[maxn];struct node{    int item;    int id;}p;bool operator<(node a,node b) {       if(num[a.id]==num[b.id])        return a.id<b.id;       return num[a.id]<num[b.id];}set<node>st;set<node>::iterator it;int main(){    int t;    int n;    Ri(t);    W(t)    {st.clear();         Ri(n);        memset(dgree,0,4*n+4);        int cnt=0;        for(int i=1;i<=n;i++)        {            Ri(num[i]);            p.id=i;            it=st.upper_bound(p);            if(it==st.begin())            {                vt[cnt].pb(i);                p.item=cnt,p.id=i;                st.insert(p);                cnt++;            }            else            {                it--;                p=*it;                dgree[p.id]++;                if(dgree[p.id]==2)                    st.erase(it);                p.id=i;                st.insert(p);                vt[p.item].pb(i);            }        }        Pi(cnt);        for(int i=0;i<cnt;i++)        {            printf("%d",vt[i].size());            for(int j=0;j<vt[i].size();j++)            {                printf(" %d",vt[i][j]);            }            puts("");            vt[i].clear();        }    }return 0;}


0 0
原创粉丝点击