yzoj P2344 斯卡布罗集市 题解

Posted donkey2603089141

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了yzoj P2344 斯卡布罗集市 题解相关的知识,希望对你有一定的参考价值。

共t条街对于每一条街上有n个店铺(n可能不相同),每次只能选两端第一个营业的店铺采购,采购第i个店铺会获得幸福度ai,采购完后,这个店铺和它相邻的店铺便会关门,问最大幸福度?

考场想了一下dp,一开始想一维但发现不好处理,二维参数也没有想出来,于是便开始了我的暴力瞎搞之旅,我随手写了几个例子发现对于n为奇数无论怎么采购,幸福度是固定的为a1, a3 , a5........an于是便可以直接累加,然而对于n为偶数又怎么去处理呢?我也随手写了n为6,8,10的数据发现其实就只有三种情况。

第一种情况:选编号为奇数的

第二种情况:选编号为偶数的

第三种情况:选两头,再考虑中间,举个栗子

3 8 20 8 15 12 12 25 

对于这组数据我们选完a1 a8后再去进行选择a3 a5我们把选了用o表示没选的用x表示就是

o x o x o x x

貌似一定又两个连在一起的不选,但考场我也没去证明就直接用了,枚举这两个不选的位置就行,跑完样例发现过了便直接提交了,结果a了,自己也很懵逼。

代码

#include<bits/stdc++.h>
using namespace std;
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<<1)+(x<<3)+(ch^48);
        ch=getchar();
    
    return x*f;

int t,n;
long long f[310][1510],ans,tmp1,tmp2;
int main()
    t=read();
    for(int i=1;i<=t;++i)
        n=read();
        for(int j=1;j<=n;++j)
            f[i][j]=read();
        
        if(n&1)
            for(int j=1;j<=n;++j)
                if(j&1) ans+=f[i][j];
            
        
        else
            tmp2=0; 
            for(int j=0;j<=n;++j)
                tmp1=0;
                for(int k=1;k<j;k+=2)
                    tmp1+=f[i][k];
                
                for(int k=j+2;k<=n;k+=2)
                    tmp1+=f[i][k];
                
                tmp2=max(tmp1,tmp2);
            
            ans+=tmp2;
        
    
    printf("%lld",ans);
    return 0;

貌似可以hack掉,可能数据比较水就a了,再放一个大佬写的前缀和表达

#include<algorithm>
#include<cstdio>
#define ll long long
#define MX 10001
using namespace std;
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<<1)+(x<<3)+(ch^48);
        ch=getchar();
    
    return x*f;

int T,n;
ll ans=0;
int a[MX];
ll suml[MX],sumr[MX];
int main()
    T=read(); 
    while(T--)
        n=read();
        sumr[n+1]=0;
        for(int i=1;i<=n;++i)
            a[i]=read();
            if(i&1)
                suml[i]=suml[i-1]+a[i];
            else
                suml[i]=suml[i-1];
            
        
        if(n&1)
            ans+=suml[n];
        else
            for(int i=n;i>=1;--i)
                if(i&1)
                    sumr[i]=sumr[i+1];
                else
                    sumr[i]=sumr[i+1]+a[i];
                
            
            ll sum=0;
            for(int i=1;i<=n;++i)
                sum=max(sum,suml[i-1]+sumr[i+1]);
            
            ans+=sum;
        
    
    printf("%lld",ans);
    return 0;

以上是关于yzoj P2344 斯卡布罗集市 题解的主要内容,如果未能解决你的问题,请参考以下文章

yzoj P2371 爬山 题解

yzoj P1122 阶乘 题解

yzoj1657货仓选址 题解

yzoj2057 x 题解

yzoj P2345 战争 题解

yzoj 2372 小B的数字 题解