JS禁止查看网页源代码的简单实现方法

JZOJ 小奇采药 (深度优先搜索-dfs)

来源:JZOJ

题目描述

小奇是只天资聪颖的喵,他的梦想是成为世界上最伟大的医师。

为此,他想拜喵星球最有威望的医师为师。

医师为了判断他的资质,给他出了一个难题。

医师把他带到一个到处都是草药的山洞里对他说:

“小奇,这个山洞里有一些不同的草药,采每一株都需要一些时间,每一株也有它自身的价值。

我会给你一段时间,在这段时间里,你可以采到一些草药。

如果你是一只聪明的喵,你应该可以让采到的草药的总价值最大。”

解题思路

  • 这道题乍一看,还以为就是个背包的模板题,细细一看...不就是道模板题嘛!
  • 信心满满地以瞬雷不及掩耳之势 打好了代码,提交!!!
  • 30 分!QAQ
  • 原来,这道题 要用 搜索!
  • 哈哈!惊异到了吧!让我们来正经地理一下思路:
  • 数据有点坑,所以,有请 dfs 中的玄学——剪枝 登场!
  • 先按时间从大到小排序,求一个后缀和,sw[i] 表示 in 的时间和,sv[i] 表示 in 的价值和,然后就做一个背包的 dfs 吧!

剪枝技巧:

  • First:如果当前的时间和加上 a[n].w 还超过了背包容量,也就是不管那哪一件往背包里塞都装不下了,就退出
  • Second:如果当前的价值和加上 sv[x] 也就是说 x 后的价值和仍然小于最优值,就退出
  • Third:如果当前的时间和加上 sw[x] 也就是说 x 后的时间和小于背包容量,就拿当前的价值和加上 sv[x] 和原最优解比较,如果当前的更优,更新,这时候就没有再递归下去的必要了,直接退出
  • :也许思路有些别扭,静下心来,仔细思考一下,这三个剪枝是很有效的

Code

#include <bits/stdc++.h> using namespace std; long long ans=0; long long sw[205],sv[205]; int n; long long m; struct node { int w,v; }a[205]; 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*10+ch-'0';ch=getchar();} return x*f; } bool mycmp(node a,node b) { return a.w>b.w; } void dfs(int x,long long sumw,long long sumv) { ans=max(ans,sumv); if (sumw+a[n].w>m) return; //三个剪枝,上文已给出 if (sumv+sv[x]<ans) return; if (sumw+sw[x]<=m) { ans=max(ans,sumv+sv[x]); return; } if (sumw+a[x].w<=m) dfs(x+1,sumw+a[x].w,sumv+a[x].v); //如果可以取当前这个,递归 dfs(x+1,sumw,sumv); //不取 } int main() { freopen("herb.in","r",stdin); freopen("herb.out","w",stdout); int T; T=read(); for (int t=1;t<=T;t++) { scanf("%d %lld",&n,&m); for (int i=1;i<=n;i++) scanf("%d %d",&a[i].w,&a[i].v); sort(a+1,a+n+1,mycmp); //按时间从大到小排序 sw[n+1]=0; sv[n+1]=0; //初值,因为是递推,所以没必要memset for (int i=n;i>=1;i--) //后缀和 { sw[i]=sw[i+1]+a[i].w; sv[i]=sv[i+1]+a[i].v; } ans=0; dfs(1,0,0); printf("%lld\n",ans); //输出最优值 } return 0; }

__EOF__

本文作者Admin-zx
本文链接https://www.cnblogs.com/Michael-zx/p/12357738.html
关于博主:评论和私信会在第一时间回复。或者直接私信我。
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!
声援博主:如果您觉得文章对您有帮助,可以点击文章右下角推荐一下。您的鼓励是博主的最大动力!
posted @   Z__X  阅读(328)  评论(0编辑  收藏  举报
编辑推荐:
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
阅读排行:
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· 没有Manus邀请码?试试免邀请码的MGX或者开源的OpenManus吧
· 园子的第一款AI主题卫衣上架——"HELLO! HOW CAN I ASSIST YOU TODAY
· 【自荐】一款简洁、开源的在线白板工具 Drawnix
点击右上角即可分享
微信分享提示