送礼物(双向DFS)

双向DFS

171.送礼物(dfs排序+二分)

![在这里插入图片描述]( https://img-blog.csdnimg.cn/8d74a8ed6f0f476db31e271b03dd2734.png?x-oss-process=image/watermark ,type_ZHJvaWRzYW5zZmFsbGJhY2s,shadow_50,text_Q1NETiBAUGFuc2XCtw==,size_20,color_FFFFFF,t_70,g_se,x_16)

样例输入:

20 5
7
5
4
18
1

样例输出:

19

代码模板:

#include<iostream>
#include<cstdio>
#include<algorithm>
using namespace std;

typedef long long LL;
const int N = 1<<24;
int w,n,g[N];
int weight[N],k,cnt;
int ans;
void dfs(int u,int s){
	if(u==k){
		weight[cnt++]=s;
		return;
	}
	
	if((LL)s+g[u]<=w) dfs(u+1,s+g[u]);
	
	dfs(u+1,s);
}

void dfs2(int u,int s){
	if(u==n){
		int l=0,r=cnt-1;
		while(l<r){
			int mid=l+r+1>>1;
			if(weight[mid]+(LL)s>w) r=mid-1;
			else l=mid; 
		}
		if((LL)s+weight[r]<=w) ans=max(ans,weight[r]+s);
		
		return;
	}
	
	if((LL)s+g[u]<=w) dfs2(u+1,s+g[u]);
	
	dfs2(u+1,s);
}

int main(){
	cin>>w>>n;
	
	for(int i=0;i<n;i++) cin>>g[i];
	
	sort(g,g+n);
	
	reverse(g,g+n);
	
	k=n/2+2;
	
	dfs(0,0);
	
	sort(weight,weight+cnt);
	int t=1;
	for(int i=1;i<cnt;i++)
	    if(weight[i]!=weight[i-1])
	    	weight[t++]=weight[i];
	    	
	cnt=t;
	
	dfs2(k,0);
	
	cout<<ans<<endl;
	
	return 0;
} 

 

posted @ 2022-03-22 14:50  panse·  阅读(38)  评论(0)    收藏  举报