• CF 637 div2


    有空补上。

    A题:

    题意:t个测试数据,每个数据给出n个数,每个数在[a-b,a+b],询问n个数的和是否在[c-d,c+d]上。

    分析:直接判断n个数的最大值是否小于c-d或者最小值大于c+d,满足的话输出No。否则输出Yes。

    代码:

     1 #include <iostream>
     2 #include <cstdio>
     3 using namespace std;
     4 int t,n,a,b,c,d;
     5 int main(void)
     6 {
     7     scanf("%d",&t);
     8     while(t--)
     9     {
    10         scanf("%d %d %d %d %d",&n,&a,&b,&c,&d);
    11         if(n*(a-b)>c+d||n*(a+b)<c-d)printf("No
    ");
    12         else printf("Yes
    ");
    13     }
    14     return 0;
    15 }

    B题:

    题意:对每一个例给出一组数据,求该组数据中一个长度为k的区间的最大山峰数以及该区间的左下标。

    分析:对每一个山峰?(英语不好)做一个标记,然后设置一个长度为k的区间,从1到k,然后将这个区间滑动到最后,过程中更新最大山峰数以及区    间左下标。怎么更新呢?设置一个变量now记录当前的山峰数,向右滑动时如果加入的点是标记点的后一个,那么now++;出去的点如果是标记点的前一个,  now--。最后输出即可。

    代码:

     1 #include <iostream>
     2 #include <cstdio>
     3 using namespace std;
     4 int t,n,k,a[210000],f[210000];
     5 int main(void)
     6 {
     7     scanf("%d",&t);
     8     while(t--)
     9     {
    10         scanf("%d %d",&n,&k);
    11         for(int i=1;i<=n;i++)
    12         {
    13             scanf("%d",&a[i]);
    14             f[i]=0;
    15         }
    16         for(int i=2;i<n;i++)
    17         {
    18             if(a[i]>a[i+1]&&a[i]>a[i-1])f[i]=1;
    19         }
    20         int maxx=0,now=0,left=1;
    21         for(int i=2;i<k;i++)
    22         {
    23             if(f[i])now++;
    24         }
    25         maxx=maxx>now?maxx:now;
    26         for(int i=k+1;i<=n;i++)
    27         {
    28             if(f[i-1])now++;
    29             if(f[i-k+1])now--;
    30             if(now>maxx)
    31             {
    32                 maxx=now;
    33                 left=i-k+1;
    34             }
    35         }
    36         printf("%d %d
    ",maxx+1,left);
    37     }
    38     return 0;
    39 }

    C题:

    题意:(理解了好久)对每组排列,判断生成器能否生成该组排列,生成器生成排列规则如下:

    1.对于每一个下标j,1<=j<=n,rj等于后面最近的空位下标,否则为0。

    2.对于每一个下标t,cntt等于rj=t的数量(1<=j<=n),如果该位置被占用则无效。

    3.生成器必须取cntt最大的位置存放当前的数,如果不止一个最大,那可以在这些位置中任意选择。

    分析:首先存放的数对cnt和r没有影响,关键是存放的位置,容易知道一开始没有放任何数时,所有的cntt都等于1,假设我们第一个是存放的位置是i,那么就有两种情况:

    (1)i=n,也就是放在最后一位,此时cnt n无效,而其他的所有cntt仍为1,因为对1<=j<=n,rj=j;所有对1<=t<=n-1,cntt=1。我们接下来相当于来到把n-1个数放进n-1个位置,相比原来仅仅少了一个数。

    (2)i<n,此时ri=i+1,ri+1=i+1,cnti无效,而cnti+1=2,其他所有cntt=1,因此下一个数只能存放在i+1位置,而这又导致cnti+2最大,从而得到结论:如果这个位置紧邻着下一个空位,那么下一个数必定存在下一个空位。

    最后思路便是:对于1<=i<n,a[i+1]==a[i]+1 or a[i+1]<a[i],否则不能生成该排列。

    代码:

     1 #include <iostream>
     2 #include <cstdio>
     3 using namespace std;
     4 int t,n,p[110000];
     5 int main(void)
     6 {
     7     cin>>t;
     8     while(t--)
     9     {
    10         cin>>n;
    11         for(int i=1;i<=n;i++)cin>>p[i];
    12         int i;
    13         for(i=2;i<=n;i++)
    14         {
    15             if(p[i]>p[i-1]+1)break;
    16         }
    17         if(i<=n)printf("No
    ");
    18         else printf("Yes
    ");
    19     }
    20     return 0;
    21 }
  • 相关阅读:
    python基础—函数装饰器
    python基础—函数嵌套与闭包
    Python之三级菜单
    Python之运算符
    Python之字典
    Python之购物车
    Python之列表
    Python之布尔
    Python之“Hello World”
    Python之递归函数
  • 原文地址:https://www.cnblogs.com/yanying7/p/12767229.html
Copyright © 2020-2023  润新知