USACO 2016 Jan Bronze 2.Angry Cows 愤怒的奶牛

题目描述
大概的意思就是一个数轴上有n个不重复的点 然后你放一个点在数轴上的某处,那么他会传递以一为半径内的所有点,然后被传递的点会继续传递,传递的半径加一 ,一直传递下去 求能够被传递的点的个数的最大值
Input
第一行 一个数n
下面n行 表示数轴上的点的位置
output
一行一个数,如题目所述

想法

01.孩子们,你们的宽搜,都是干什么吃的。。。。。。。不用我教吧。。。自己写去吧
02.我们发现在一个大概长为1e9 的线段上只有那么几个可怜的点,这是有多么离散啊。。。。。你们想一想,有一些点前不着村,后不着店,删了就行。。。
03.你们说什么,麻烦,好啊,那我们就进行简化:
减来减去的太麻烦?TAT?
差分数组将会是你的好伙伴。。。。。
什么 中间的点扩展没有意义?偶。。那就递归着扩展呗。。。只考虑边界
啊?为什么在左面拓展过的点还要重新的拓展呢?
对啊
那你就别向右拓展呗(左面同理。。。)
啊 你说什么 有些点的拓展并没有什么用
你们自己贪心啊
04.什么,你说点其实没有必要去管那些奇怪的间隙
啊 对啊
确实没有什么必要其实你把他放在旁边(不管有没有点都可以)到达那个位置的时候的深度都可以看成深度为2

这么说来 这道题至少有两大种方法n种优化

有点水
。。。。。
但是开始我挂了。。。。。。。。

#include <stdio.h>
#include <string.h>
#include <algorithm>
#include <iostream>
using namespace std;
#define inf 2000
#define MAXN 100+5
int ans=-1;
inline int read()
{
    int x = 0, f = 1; char ch = getchar();
    while (ch < '0' || ch > '9') { if (ch == '-') f = -1; ch = getchar(); }
    while (ch >= '0' && ch <= '9') { x = x * 10 + ch - '0'; ch = getchar(); }
    return x * f;
}
int l,r,n,a[MAXN],cha[MAXN],vis[MAXN];
void exe_l(int x,int depth)
{
    int tmp1=x,tmp2=depth,flag=false;
    while( tmp1 && tmp2 )
    {
        if(cha[tmp1-1]<=tmp2)
            tmp2-=cha[--tmp1],flag=true;
        else
            break;
    }
    if(flag)
        exe_l(tmp1,depth+1);
    else
        l=tmp1;
    return;
}
void exe_r(int x,int depth)
{
    int tmp1=x,tmp2=depth,flag=false;
    while(tmp1<=n &&depth)
    {
        if(cha[tmp1]<=depth)
            tmp2-=cha[tmp1++],flag=true;
        else
            break;
    }
    if(flag)
        exe_r(tmp1,depth+1);
    else
        r=tmp1;
    return;
}
int main()
{
    cin>>n;
    for(int i=1;i<=n;++i)
        a[i]=read();
    sort(a+1,a+n+1);
    for(int i=1;i<=n;++i)
        cha[i-1]=a[i]-a[i-1];
    cha[0]=cha[n]=inf;
    for(int i=1;i<=n;++i)
    {
        if(vis[i])
            continue;
        l=inf,r=0;
        exe_l(i,1);
        exe_r(i,1);
        ans=max(r-l+1,ans);
    } 

    cout<<ans;

}

囧。。。

你可能感兴趣的:(搜索,USACO,水)