取数游戏2

取数游戏2

https://ac.nowcoder.com/acm/problem/14701

题目描述

给定两个长度为n的整数列A和B,每次你可以从A数列的左端或右端取走一个数。假设第i次取走的数为ax,则第i次取走的数的价值vi=bi⋅ax,现在希望你求出∑vi的最大值。

输入描述:

第一行一个数T,表示有T组数据。
对于每组数据,第一行一个整数n,
接下来两行分别给出A数列与B数列。

输出描述:

每一组数据输出一行,最大的∑vi。

题解

这道题还是很好想的,我们每次做的决策就是是选最左端的还是选择最右端的。我们可以设置dp[i][j]表示剩下的区间是从i到j的,也就是我们选了1~i-1和j+1到n。那么很明显,dp[i][j]=max(dp[i-1][j]+a[i]b[k],dp[i][j+1]+a[j]b[k])。在枚举的时候我们可以直接枚举前面选几个来算出后面的位置。

代码

#include<bits/stdc++.h>
using namespace std;
int a[1050],b[1050];
long long dp[1050][1050];
int main(){
    int T;
    cin>>T;
    while(T--){
        int n;
        cin>>n;
        for(int i=1;i<=n;++i)cin>>a[i];
        for(int i=1;i<=n;++i)cin>>b[i];
        long long ans=0;
        for(int i=1;i<=n;++i){
            for(int j=0;j<=i;++j){
                if(!j)dp[j][n-i+j+1]=dp[j][n-i+j+2]+a[n-i+j+1]*b[i];
                else if(i==j)dp[j][n-i+j+1]=dp[j-1][n-i+j+1]+a[j]*b[i];
                else dp[j][n-i+j+1]=max(dp[j][n-i+j+2]+a[n-i+j+1]*b[i],dp[j-1][n-i+j+1]+a[j]*b[i]);
                ans=max(ans,dp[j][n-i+j+1]);
                //cout<<j<<" "<<n-i+j+1<<" "<<dp[j][n-i+j+1]<<endl;
            }
        }
        cout<<ans<<endl;
    }
}
杂题题解 文章被收录于专栏

各种各样题目的题解

全部评论

相关推荐

06-06 03:40
已编辑
电子科技大学 Java
在秋招的小白菜很想养修勾:一眼 苍穹外卖+谷粒商城,项目换一换吧,可以找一些付费知识星球博主带带,避免烂大街。多投投大厂,背背八股,你这学历乱杀了,等实习经验到位,到时候大厂闭眼选
投递美团等公司7个岗位
点赞 评论 收藏
分享
大方的大熊猫准备进厂:1.教育背景:你希望从事什么专业的工作你的主修课就是什么;成绩优秀是你应该做的,没什么可描述的,成绩不优秀也许人家在大学忙着创业呢?(成绩优秀不一定是好事,只能说明多元化的大学你上成了高中,没有真正上明白大学,反而体现了你死板,不爱社交,没有别的突出能力) 2.实践经历:你想表达的意思没有说清楚。你是说你会个性化服务,还是你有实习经历。如果没有带来,经济收益,表彰,更好的发展前景,那你还不如说说提升了自己哪些技能。你说有人给你送锦旗我都能明白你优秀,但是你说你会xxxx,你说这话谁信,证据呢。 3.入伍经历:你描述的就是你的工作职责或者你应该做的,并没有体现出来你把这个事情做好了,而且入伍经历并不能证明你能干好你要应聘的工作,不如只写经历其余所有内容都不写。 4.荣誉技能:重点突出一下,但不要过多描述,这些荣誉的含金量懂得都懂。 重点:你要应聘什么工作(具体岗位,实习生不具体),你的期望薪资
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务