题面:
题意:
①塞斯石是一种重要的东西,以塞斯(Si)为单位。
②本来是单独存在,经过特殊处理后可以合并,合并后也可以切开
③现在有一定量(Need)的塞斯石需要上市,卖家需要租船送赛斯石过去,目前有十种船可以租,载重量从 1Si 到 10si ,每艘船的租价也是有所不同的,如下表所示:

④给定 1Si ~ 10Si 的市场价,求完成后的最大利润
说人话:
给你一定的需求,可以合并,每个Si都有相对的代价,求合并完后的最大利润
(可以试着正着思考10min再食用效果更佳)
思路:
10min过去了,你会发现正着做几乎不可取(你要是非想正着写我也不拦着),要处理的因素太多,合并和分解有点难搞,那我们换种方法来:
①石头可以分割但是船不可以
例子:比如说4Si可以分割成
1+1+1+1Si
1+1+2Si
1+3Si
2+2Si
4Si
②最后可以选择总和为Need的船,且每个船的利益都是固定的
例子:不需要
通过上述两点,开动你聪明的小脑瓜看看这是什么道什么题
相信聪明(bushi)的你已经看出来这是个完全背包了(而且还是很裸的那种),看不出来的可以考虑退役了
接下来就是喜闻乐见的代码了(就是一个不用动脑子的板子)
#include<bits/stdc++.h>
using namespace std;
long long 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*10+ch-'0';ch=getchar();}
return x*f;
}
int n;
int a[12];
int b[12]={0,1,3,5,7,9,10,11,14,15,17};
long long f[100010];
long long dp[100010];
int main()
{
n=read();
for(int i=1;i<=10;i++)
{
a[i]=read();
}
for(int i=1;i<=10;i++)
{
for(int j=i;j<=10;j++)
{
f[j]=max(f[j],f[j-i]+a[i]);
}
}
for(int i=1;i<=n;i++) f[i]-=b[i];
for(int i=1;i<=10;i++)
{
for(int j=i;j<=n;j++)
{
dp[j]=max(dp[j],dp[j-i]+f[i]);
}
}
cout<<dp[n]<<endl;
return 0;
}
总结
本题考验的是学生的思维能力,只要把思维从石头转换为船就能轻易解决本道题,事实告诉我们:正着磕不出来的题,可以试试从反面磕一磕,若还是不行,可以考虑开下一题了换个思路再试一试,拿着题就磕容易吃瘪(磕了半小时后的惨痛经验),实在不行就先留着,等下面的题答完后就可以回来接着磕。(这道题如果想不到背包的话,可以试试暴搜拿个部分分)
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】