题目大意

1.题目描述

斜堆(skew heap)是一种常用的数据结构。
它也是二叉树,且满足与二叉堆相同的堆性质:
每个非根结点的值都比它父亲大。因此在整棵斜堆中,根的值最小。
.
但斜堆不必是平衡的,每个结点的左右儿子的大小关系也没有任何规定。
在本题中,斜堆中各个元素的值均不相同。
.
在斜堆\(H\)中插入新元素\(X\) 的过程是递归进行的:
(1)当\(H\)为空或者\(X\)小于\(H\)的根结点时,
\(X\)变为新的树根,而原来的树根(如果有的话)变为\(X\)的左儿子。
.
(2)当\(X\) 大于\(H\) 的根结点时,
\(H\)根结点的两棵子树交换,而\(X\)(递归)插入到交换后的左子树中。
.
给出一棵斜堆,包含值为\(0\)到\(n\)的结点各一次。
求一个结点序列,使得该斜堆可以通过在空树中依次插入这些结点得到。
如果答案不惟一,输出字典序最小的解。输入保证有解。
.
数据范围\(n \leq 50\)

2.样例文件:

input1:
6
100 0 2 102 4 104
output1:
4 6 5 2 0 1 3
..............................................................
input2:
7
0 100 1 102 2 3 5
output2:
2 5 0 3 4 6 7 1

思路及解法:

本题的数据范围出到\(n \leq 5 \times 10^3\)是肯定没问题的。
所以总结一下,本题时间复杂度\(O(n^2)\),空间复杂度\(O(n)\),思维复杂度\(O(n!)\)....
.
言归正传,这题到底怎么做?
由于每次都是插入左子树中,所以就会有一些神奇的事情。
我们考虑 最后一个插入的点 会有什么性质:
(1)性质1:它是一个极左节点(从根到它的路径都是走左子树)
(2)性质2:它一定没有右子树
显然满足上述条件的点有很多,那么仔细观察后可以发现:
性质3:对于树上任意一个点,如果它没有左子树,则它一定没有右子树
.
然后就可以搞一波事情了。
我们假设最后加入的点为 \(X\) ,如果它的祖先中存在点 \(Y\) 也满足性质\(1,2\),则:
<1>
若\(X\)不为叶子节点:
由于\(X\)插入\(Y\)的子树中时会反转\(Y\)的左右儿子,
那么\(Y\)的当前左子树中包含\(X\),而现在\(Y\)又没有右子树,
所以在插入前,\(Y\)只有右子树,没有左子树。
这显然与性质3矛盾,即这种情况不可能发生。
所以最后插入的点一定是 深度最浅的满足性质1,2的节点,设它为 \(del1\)。
<2>
若\(X\)为叶子节点:
那么即插入\(X\)前\(Y\)没有儿子。
所以这种情况显然是合法的,
即如果\(del1\)有左儿子\(del2\),且\(del2\)为叶子节点,那么\(del2\)也是合法的。
.
综上所述,最后插入的点可能为:
(1)深度最浅的满足性质1,2的节点
(2)深度最浅的满足性质1,2的节点的左儿子,前提是这个左儿子为叶子节点。
由于我们要保证字典序,所以存在(2)情况时我们则优先选叶子节点。
所以我们依照这个原则不断删点、修改。
最后把答案数组倒着输出即可(P.s :建议把所有点的编号都加\(1\)再处理)。

实现代码:

#include<bits/stdc++.h>
#define RG register
#define IL inline
#define mx 60
#define ll long long
using namespace std;

int n,root,fa[60],ls[60],rs[60],ans[60];

IL void Work(){
    for(RG int sq = 1; sq <= n; sq ++){
        RG int del1 = 0 , del2 = 0, x = root;
        while(x){ if(!rs[x]){del1 = x; break;} x = ls[x]; }
        if(!rs[ls[x]] && !ls[ls[x]] && ls[x])
            del2 = ls[x];
        if(del2){ans[sq] = del2; ls[del1] = 0; }
        else {
            ans[sq] = del1;
            ls[fa[del1]] = ls[del1]; fa[ls[del1]] = fa[del1];
        }
        if(!del2 && del1 == root)root = ls[del1] , fa[root] = 0;;
        RG int ff = fa[(del2)?del2 : del1];
        while(ff)
            swap(ls[ff],rs[ff]) , ff = fa[ff];
    }return;
}

int main(){
    cin >> n; n++; root = 1;
    for(RG int i = 2,f; i <= n; i ++){
        cin >> f;
        if(f >= 100){f-=100; f++; rs[f] = i; fa[i] = f;}
        else f++ , ls[f] = i , fa[i] = f;
    }
    Work();
    for(RG int i = n; i >= 1; i --)ans[i] --;
    for(RG int i = n; i >= 1; i --)cout<<ans[i]<<" ";
    return 0;
}

[SCOI2008]斜堆的更多相关文章

  1. BZOJ 1078: [SCOI2008]斜堆

    1078: [SCOI2008]斜堆 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 770  Solved: 422[Submit][Status][ ...

  2. 【bzoj1078】[SCOI2008]斜堆

    2016-05-31 16:34:09 题目:http://www.lydsy.com/JudgeOnline/problem.php?id=1078 挖掘斜堆的性质233 http://www.cp ...

  3. 【BZOJ1078】[SCOI2008]斜堆(性质题)

    [BZOJ1078][SCOI2008]斜堆(性质题) 题面 BZOJ 洛谷 题解 考虑一下这道题目的性质吧.思考一下最后插入进来的数是什么样子的.首先因为它是最后插入进来的,所以一定是比某个数小,然 ...

  4. 【BZOJ 1078】 1078: [SCOI2008]斜堆

    1078: [SCOI2008]斜堆 Description 斜堆(skew heap)是一种常用的数据结构.它也是二叉树,且满足与二叉堆相同的堆性质:每个非根结点的值都比它父亲大.因此在整棵斜堆中, ...

  5. BZOJ1078 [SCOI2008]斜堆 堆

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ1078 题意概括 斜堆(skew heap)是一种常用的数据结构.它也是二叉树,且满足与二叉堆相同的 ...

  6. P2475 [SCOI2008]斜堆(递归模拟)

    思路 可并堆真是一种神奇的东西 不得不说这道题是道好题,虽然并不需要可并堆,但是能加深对可并堆的理解 首先考虑斜堆的性质,斜堆和左偏树相似,有如下的性质 一个节点如果有右子树,就一定有左子树 最后插入 ...

  7. 【bzoj1078】 SCOI2008—斜堆

    http://www.lydsy.com/JudgeOnline/problem.php?id=1078 (题目链接) 题意 给出一个斜堆,并给出其插入的操作,求一个字典序最小的插入顺序. Solut ...

  8. P2475 [SCOI2008]斜堆

    题目背景 四川2008NOI省选 题目描述 斜堆(skew heap)是一种常用的数据结构.它也是二叉树,且满足与二叉堆相 同的堆性质:每个非根结点的值都比它父亲大.因此在整棵斜堆中,根的值最小. 但 ...

  9. [bzoj1078][SCOI2008][斜堆] (贪心)

    Description 斜堆(skew heap)是一种常用的数据结构.它也是二叉树,且满足与二叉堆相同的堆性质:每个非根结点的值都比它父亲大.因此在整棵斜堆中,根的值最小.但斜堆不必是平衡的,每个结 ...

随机推荐

  1. Eclipse Java,debug模式无法调试,调试按钮不可用时解决办法

    经常出现debug模式进入后,debug的几个按钮置灰,F5,6,8,没有任何反应时,这样操作: 退出 Eclipse.打开 Eclipse 目录下的 configuration 下的 org.ecl ...

  2. jumpserver在centos 7上的部署

    cd /opt/git clone https://github.com/jumpserver/jumpserver.gitcd jumpservergit checkout master 准备安装: ...

  3. SDP(8):文本式数据库-MongoDB-Scala基本操作

    MongoDB是一种文本式数据库.与传统的关系式数据库最大不同是MongoDB没有标准的格式要求,即没有schema,合适高效处理当今由互联网+商业产生的多元多态数据.MongoDB也是一种分布式数据 ...

  4. bzoj 1814 Ural 1519 Formula 1 插头DP

    1814: Ural 1519 Formula 1 Time Limit: 1 Sec  Memory Limit: 64 MBSubmit: 942  Solved: 356[Submit][Sta ...

  5. AVFoundation 框架初探究(四)

    叨叨两句 动手写这篇总结时候也是二月底过完年回来上班了,又开始新的一年了,今年会是什么样子?这问题可能得年底再回答自己了.在家窝了那么久,上班还是的接着看我们要看的东西,毕竟我们要做的事还真的太多的. ...

  6. TP3.2 中使用 PHPMailer 发送邮件

    第一步.添加PHPMailer类库 http://pan.baidu.com/s/1o7Zc7V0 第二步.添加发送邮件函数 在common目录中的公共函数文件加入函数 <?php /***** ...

  7. 《android开发进阶从小工到专家》读书笔记--HTTP网络请求

    No1: 客户端与服务器的交互流程: 1)客户端执行网络请求,从URL中解析出服务器的主机名 2)将服务器的主机名转换成服务器的IP地址 3)将端口号从URL中解析出来 4)建立一条从客户端与Web服 ...

  8. CodeForces-748D 贪心

    这题的思维难度不是很大,属于编程实现细节处理较多的题. 暂且把每个字符串的"beauty"称为魅力值,用一个优先队列数组将同一个字符串的所有魅力值保存,通过map将不同字符串编号, ...

  9. struts2框架概述

    框架概述 什么是框架,为什么使用框架,框架优点 框架(framework)是一个基本概念上的结构,用于去解决或者处理复杂的问题 框架,即framework.其实就是某种应用的半成品,就是一组组件,供你 ...

  10. Python基础学习参考(七):字典和集合

    一.字典 字典跟列表一样是一组数据的集合.它的特点是什么呢? 特点一:字典具有键(key)和值(value),其中键必须是唯一的,不可重复的,即键必须可以哈希的.对于值没有要求. 特点二:字典是无序的 ...