APIO2007-2015题解大集合(2007年篇)

   

      系列题解总述

        最近一周都在刷历年的APIO题,发现网上APIO的题解并不是很多,正好做了感觉这些题都挺有意思的,于是准备发一个APIO2007到2015年这9年题目的题解集合(好像还没人做过这件事情……)APIO给我的感觉是有很多题比较考思维,也有写起来需要很多细节的题。有意思的是,APIO并没有出现过中国特色数据结构(给你一个序列,支持XXXX操作,来个可持久化树套树看出题人心情带不带垃圾回收……),尽管2010年是中国出题;相反,APIO中很多题目是贪心和DP,这也是能够充分考验一个选手的分析能力的题目类型。

        另外:之后的题目中,如果出现了【上古预警】,则代表这些题目是作者很早的时候做的,记忆可能比较搓,方法比较笨,代码风格可能比较丑……

      风铃【上古预警】

                首先由于层数在交换过程中不能变化,显然如果一开始就存在相差超过2层的情况必然无解。
                然后考虑“合并”两个分支的情况。现在风铃有可能在上一层(我们定义为“高”),也可能在下一层(我们定义为“矮”)。我们认为一个子树具有三种状态:纯高,纯矮和          高矮兼有。令f[x]为x子树交换成满足条件的交换次数,则显然有f[x]=f[son1]+f[son2]+k,k视两边的情况而定。
                下面是具体情况:(下面只介绍左右儿子均有的情况,只有一个儿子的情况留给读者自行思考)
                1、左边复杂,右边纯高,k=0;
                2、左边复杂,右边纯矮,k=1;
                3、左右一样,k=0;
                4、左边纯高,k=1;
                5、右边纯矮,k=1;
                然后就是注意特判和爆栈的问题了。作者写这个代码的时候还没学手工栈,所以用了一种讨巧的方法(详见代码)     
#include<iostream>
#include<iomanip>
#include<algorithm>
#include<cstring>
#include<cstdio>
#include<cstdlib>
#include<cmath>
using namespace std;
//基本思路:判断无解:首先如果在图中一开始就有层数差距大于1,则不可能成功。
//否则,肯定是能成功的。
//这样我们可以对左右的“纯”和“不纯”进行讨论 
int n,maxd=0,mind=999999999,deep[100005]={0},d[100005]={0},l[100005]={0},r[100005]={0};
int f[100005]={0};
bool high[100005]={0};
int pure[100005]={0};
void input()
  {scanf("%d",&n);
   for(int i=1;i<=n;i++)
     {scanf("%d%d",&l[i],&r[i]);
	  }
   }
void dfs(int x,int depth)
  {deep[x]=depth;
   //cout<<x<<' '<<depth<<endl;
   if(l[x]==-1||r[x]==-1)
     {maxd=max(maxd,depth+1),mind=
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值