• bzoj 2151 种树


    题目大意:

    n个数组成的环中取m个互不相邻的数使这些数和最大

    思路:

    贪心 先用链表把数存起来

    然后每次选一个最大的$a[x]$,把链表左右两边的删掉

    把这个值替换为$a_{left[x]}+a_{right[x]}-a_x$ 这样在堆里重复m次即可

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstdlib>
     4 #include<cmath>
     5 #include<algorithm>
     6 #include<cstring>
     7 #include<vector>
     8 #include<stack>
     9 #include<queue>
    10 #include<map>
    11 #define rep(i,s,t) for(register int i=(s),i__end=(t);i<=i__end;++i)
    12 #define dwn(i,s,t) for(register int i=(s),i__end=(t);i>=i__end;--i)
    13 #define ren for(int i=fst[x];i;i=nxt[i])
    14 #define Fill(x,t) memset(x,t,sizeof(x))
    15 #define ll long long
    16 #define ull unsigned long long
    17 #define inf 1LL<<60
    18 #define MAXN 200100
    19 #define MOD 998244353
    20 using namespace std;
    21 inline int read()
    22 {
    23     int x=0,f=1;char ch=getchar();
    24     while(!isdigit(ch)) {if(ch=='-') f=-1;ch=getchar();}
    25     while(isdigit(ch)) {x=x*10+ch-'0';ch=getchar();}
    26     return x*f;
    27 }
    28 int n,m,g[MAXN],ans,r[MAXN],l[MAXN],vis[MAXN];
    29 struct data {int id,val;};
    30 bool operator < (const data a,const data b) {return a.val<b.val;}
    31 bool operator == (const data a,const data b) {return a.val==b.val&&a.id==b.id;}
    32 priority_queue <data> q;
    33 void work()
    34 {
    35     while(vis[q.top().id]) q.pop();data x=q.top();ans+=x.val;q.pop();
    36     g[x.id]=g[l[x.id]]+g[r[x.id]]-g[x.id],vis[l[x.id]]=vis[r[x.id]]=1;
    37     q.push((data){x.id,g[x.id]});r[l[l[x.id]]]=l[r[r[x.id]]]=x.id;
    38     l[x.id]=l[l[x.id]],r[x.id]=r[r[x.id]];
    39 }
    40 int main()
    41 {
    42     n=read(),m=read();if(m>(n>>1)) {puts("Error!");return 0;}rep(i,1,n) g[i]=read(),q.push((data){i,g[i]});
    43     rep(i,1,n) l[i]=i-1,r[i]=i+1;l[1]=n,r[n]=1;rep(i,1,m) work();printf("%d
    ",ans);
    44 }
    View Code

    bzoj 1150 数据备份

    几乎同上,由于一定选相邻的两个建筑,将问题转换为n-1个数构成的链取$m$个互不相邻的数使和最大

    做的时候开一个空节点,构成环,该点值为inf

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstdlib>
     4 #include<cmath>
     5 #include<algorithm>
     6 #include<cstring>
     7 #include<vector>
     8 #include<stack>
     9 #include<queue>
    10 #include<map>
    11 #define rep(i,s,t) for(register int i=(s),i__end=(t);i<=i__end;++i)
    12 #define dwn(i,s,t) for(register int i=(s),i__end=(t);i>=i__end;--i)
    13 #define ren for(int i=fst[x];i;i=nxt[i])
    14 #define Fill(x,t) memset(x,t,sizeof(x))
    15 #define ll long long
    16 #define ull unsigned long long
    17 #define inf 1000000007
    18 #define MAXN 1001000
    19 #define MOD 998244353
    20 using namespace std;
    21 inline int read()
    22 {
    23     int x=0,f=1;char ch=getchar();
    24     while(!isdigit(ch)) {if(ch=='-') f=-1;ch=getchar();}
    25     while(isdigit(ch)) {x=x*10+ch-'0';ch=getchar();}
    26     return x*f;
    27 }
    28 int n,m,g[MAXN],r[MAXN],l[MAXN],vis[MAXN];
    29 ll ans;
    30 struct data {int id;ll val;};
    31 bool operator < (const data a,const data b) {return a.val>b.val;}
    32 priority_queue <data> q;
    33 void work()
    34 {
    35     while(vis[q.top().id]) q.pop();data x=q.top();ans+=x.val;q.pop();
    36     g[x.id]=g[l[x.id]]+g[r[x.id]]-g[x.id],vis[l[x.id]]=vis[r[x.id]]=1;
    37     q.push((data){x.id,g[x.id]});r[l[l[x.id]]]=l[r[r[x.id]]]=x.id;
    38     l[x.id]=l[l[x.id]],r[x.id]=r[r[x.id]];
    39 }
    40 int main()
    41 {
    42     n=read(),m=read();rep(i,1,n) g[i]=read();rep(i,1,n-1) g[i]=g[i+1]-g[i];
    43     rep(i,1,n-1) q.push((data){i,g[i]});
    44     rep(i,1,n-1) l[i]=i-1,r[i]=i+1;l[1]=n,g[n]=inf;
    45     rep(i,1,m) work();printf("%lld
    ",ans);
    46 }
    View Code
  • 相关阅读:
    java并发
    jvm虚拟机
    L2Dwidget二次元前端添加人物插件
    MySQL数据库之rowid
    MySql支持emoji表情设置
    zookeeper不能正常启动问题(转)
    jd-gui-windows-1.6.6.zip反编译工具
    为什么es集群至少需要三个节点(转)
    超好用的uniapp弹出层
    netcore5.0 使用新的Microsoft.Data.SqlClient
  • 原文地址:https://www.cnblogs.com/yyc-jack-0920/p/10177285.html
Copyright © 2020-2023  润新知