• 北京集训DAY4


     1 /*
     2     单调队列 
     3     从左向右 每个点向右找一最近的且比他大,
     4     从右往左枚举过来 每个点 向左找最近的且比他大
     5 */
     6 #include <cmath>
     7 #include <cstdio>
     8 #include <cstdlib>
     9 #include <iostream>
    10 #include <algorithm>
    11 using namespace std;
    12 int n,s[50002],d[50002],ans[50002],ANS,a[50002],b[50002],r,i;
    13 int main()
    14 {
    15     freopen("treasure.in","r",stdin);
    16     freopen("treasure.out","w",stdout);
    17     cin>>n;
    18     for (i=1; i<=n; i++) scanf("%d%d",&a[i],&b[i]);
    19     s[1]=a[1]; d[1]=1; r=1;
    20     for (i=2; i<=n; i++)
    21     {
    22         while (r!=0 && a[i]>s[r]) { ans[i]+=b[d[r]]; r--; }
    23         r++;
    24         s[r]=a[i];
    25         d[r]=i;
    26     }
    27     s[1]=a[n]; d[1]=n; r=1;
    28     for (i=n-1; i>=1; i--)
    29     {
    30         while (r!=0 && a[i]>s[r]) { ans[i]+=b[d[r]]; r--; }
    31         r++;
    32         s[r]=a[i];
    33         d[r]=i;
    34     }
    35     for (i=1; i<=n; i++) ANS=max(ANS,ans[i]);
    36     cout<<ANS;
    37     return 0;
    38 }
    代码

     1 /*
     2     答案是连续的。
     3     如果边长为x可行,边长x+1也一定能覆盖至少C个糖果    
     4     假如x不可行,边长为x-1是不可能覆盖C个糖果的。
     5     二分答案。
     6     l=1,r=10000,  判断mid是否可行,  可行->  答案在[l,mid] ,不可行 -> (mid,r]
     7 */
     8 #include <cmath>
     9 #include <cstdio>
    10 #include <cstdlib>
    11 #include <iostream>
    12 #include <algorithm>
    13 using namespace std;
    14 struct node {int x,y;} a[1005];
    15 int C,n,L,R,mid,b[1005],o,i;
    16 int cmp(node i,node j) {return i.x<j.x;}
    17 int CMP(int i,int j) {return i<j;}
    18 bool WORK(int l,int r)
    19 {
    20      if (r-l+1<C) return false; o=0;
    21      for (int i=l; i<=r; i++) b[++o]=a[i].y;
    22      sort(b+1,b+o+1,CMP);
    23      for (int i=C; i<=o; i++)
    24        if (b[i]-b[i-C+1]<=mid) return true;
    25       return false;
    26 }
    27 bool OK(int x)
    28 {
    29     int l=1;
    30     for (int i=1; i<=n; i++)
    31     {
    32         if (a[i].x-a[l].x>x)
    33         {
    34                              if (WORK(l,i-1)) return true;
    35                              while (a[i].x-a[l].x>x) l++;
    36         }
    37     }
    38     if (WORK(l,n)) return true;
    39     return false;
    40 }
    41 int main()
    42 {
    43     freopen("square.in","r",stdin);
    44     freopen("square.out","w",stdout);
    45     scanf("%d%d",&C,&n);
    46     for (i=1; i<=n; i++)
    47         scanf("%d%d",&a[i].x,&a[i].y);
    48     sort(a+1,a+n+1,cmp);
    49     L=0; R=10000; mid=(L+R)/2;
    50     while (L<=R)
    51     {
    52           if (OK(mid)) {R=mid-1; mid=(L+R)/2;} else
    53           {
    54                        L=mid+1;
    55                        mid=(L+R)/2;
    56           }
    57     }
    58     cout<<L+1;
    59     return 0;
    60 }
    代码

     1 /*
     2     求出一个上图像和一个下图像,中间既不是最大值
     3     图像的交点,又不是最小值直线的交点,可以扔掉。
     4     斜率大的(速度大的),肯定最终到上面。所以我们按
     5     斜率进行排序,排序后插入图像(从小到大),将属于
     6     自己的位置求出,同理,下图像也可以求出。让上图
     7     像和下图像不断移动,即可求出。
     8     相当于单调栈。(右图中没有画圈的交点可以扔掉。)
     9     这道题一开始保证跑的慢的豹子一定先跑,跑的快的
    10     豹子一定后跑。
    11     我们只需要记录最上方那条线和最下方那条线
    12     被哪个豹子保管。
    13     用 f[i]表示第 i 只豹子保管了哪个区间。
    14 */
    15 #include<cstdio>
    16 #include<cstring>
    17 #include<cstdlib>
    18 #include<cmath>
    19 #include<iostream>
    20 #include<algorithm>
    21 
    22 using namespace std;
    23 const long double INF=(long double)1000000000*10;
    24 long double L,R,mid,ans,hh[100005];
    25 int r,rr,i,n,MAX,X,Y,cnt,vv[100005],vv2[100005];
    26 struct node2 {int t; long double l;} s[200005],S[200005];
    27 struct node {int t,v;} t[100005];
    28 int cmp(node i,node j) {return i.v<j.v || i.v==j.v && i.t>j.t;}
    29 struct Node {long double x;int y,z;} p[200005];
    30 int CMP(Node i,Node j) {return i.x<j.x;}
    31 long double work(int x,long double y) {return (long double)t[x].v*y-hh[x];}
    32 int main()
    33 {
    34     freopen("chase.in","r",stdin);
    35     freopen("chase.out","w",stdout);
    36     while (1)
    37     {
    38         scanf("%d",&n);
    39        // if (n==0) return 0;
    40         MAX=0;
    41         for (i=1; i<=n; i++)
    42         {
    43             scanf("%d%d",&t[i].t,&t[i].v);
    44             MAX=max(MAX,t[i].t);
    45         }
    46         sort(t+1,t+n+1,cmp); int MIN=t[n].t;
    47         for (i=n-1; i>=2; i--)
    48         {
    49             if (t[i].t>MIN) vv[i]=1; else
    50             MIN=t[i].t,vv[i]=0;
    51         }
    52         for (i=1; i<=n; i++) hh[i]=(long double)t[i].t*t[i].v;
    53         r=1; s[1].l=MAX; s[1].t=1; s[2].l=INF; vv[n]=0;
    54         for (i=2; i<=n; i++)
    55         if (!vv[i])
    56         {
    57             while (r && work(i,s[r].l)>=work(s[r].t,s[r].l)) r--;
    58             if (!r) {r=1; s[1].l=MAX; s[1].t=i; continue;}
    59             L=s[r].l; R=s[r+1].l; mid=(L+R)/2.0;
    60             for (int I=1; I<=80; I++)
    61             {
    62                 if (work(i,mid)>=work(s[r].t,mid)) {R=mid; mid=(L+R)/2.0;} else {L=mid; mid=(L+R)/2.0;}
    63             }
    64             s[++r].l=mid; s[r].t=i; s[r+1].l=INF;
    65         }
    66         rr=1; S[1].l=MAX; S[2].l=INF; S[1].t=n;
    67         MIN=t[1].t;
    68         for (i=2; i<n; i++)
    69           if (t[i].t<MIN) vv2[i]=1; else
    70             MIN=t[i].t,vv2[i]=0;
    71         for (i=n-1; i>=1; i--)
    72         if (!vv2[i])
    73         {
    74             while (rr && work(i,S[rr].l)<=work(S[rr].t,S[rr].l)) rr--;
    75             if (!rr) {rr=1; S[1].l=MAX; S[1].t=i; continue;}
    76             L=S[rr].l; R=S[rr+1].l; mid=(L+R)/2.0;
    77             for (int I=1; I<=80; I++)
    78             {
    79                 if (work(i,mid)<=work(S[rr].t,mid)) {R=mid; mid=(L+R)/2.0;} else {L=mid; mid=(L+R)/2.0;}
    80             }
    81             S[++rr].l=mid; S[rr].t=i; S[rr+1].l=INF;
    82         }
    83         cnt=0;
    84         for (i=1; i<=r; i++) {p[++cnt].x=s[i].l; p[cnt].y=1; p[cnt].z=s[i].t;}
    85         for (i=1; i<=rr; i++) {p[++cnt].x=S[i].l; p[cnt].y=0; p[cnt].z=S[i].t;}
    86         sort(p+1,p+cnt+1,CMP); X=Y=0; ans=INF;
    87         for (i=1; i<=cnt; i++)
    88         {
    89             if (p[i].y==1) X=p[i].z; else Y=p[i].z;
    90           //  printf("%.5f
    ",(double)p[i].x);
    91             if (X && Y) ans=min(ans,work(X,p[i].x)-work(Y,p[i].x));
    92         }
    93         printf("%.2f
    ",fabs((double)ans));
    94         return 0;
    95     }
    96 }
    代码
  • 相关阅读:
    PHP(运算符,语句,函数)
    数据库高级查询
    MySQL数据库常用函数
    mySQL数据库数据查询操作详解
    mySQL数据库设计范式及增删改查操作
    mySQL-创建表
    JavaScript-选项卡
    JavaScript做DIV下拉列表
    JavaScript-事件
    JavaScript函数-递归
  • 原文地址:https://www.cnblogs.com/whistle13326/p/7648780.html
Copyright © 2020-2023  润新知