[poj] 3977 Subset || 折半搜索MITM
原题
给定N个整数组成的数列(N<=35),从中选出一个子集,使得这个子集的所有元素的值的和的绝对值最小,如果有多组数据满足的话,选择子集元素最少的那个。
n<=35,所以双向dfs的O(2^(n/2))可以直接解决问题。因为会爆空间,所以枚举前一半的二进制状态来完成dfs,并用map记录每个状态所用的个数,然后枚举后一半的状态在map中找第一个大于等于他的和第一个小于他的,比较这两个答案。
注:long long 没有自带的abs,并且在define里要多打括号,因为优先度……
#include<cstdio>
#include<map>
#define abs(x) ((x)>0?(x):-(x))
typedef long long ll;
using namespace std;
ll n,a[40],ans,sum;
int cnt;
map <ll,int> mp;
map <ll,int> :: iterator qwq;
ll read()
{
ll ans=0,fu=1;
char j=getchar();
for (;(j<'0' || j>'9') && j!='-';j=getchar()) ;
if (j=='-') j=getchar(),fu=-1;
for (;j>='0' && j<='9';j=getchar()) ans*=10,ans+=j-'0';
return ans*fu;
}
int main()
{
while (~scanf("%lld",&n) && n)
{
mp.clear();
ans=0;
cnt=0;
for (int i=1;i<=n;i++)
a[i]=read();
ans=abs(a[1]);
cnt=1;
for (int i=1,j,now,count;i<(1<<(n/2));i++)
{
sum=0;
j=i;
now=0;
count=0;
while (j)
{
if (j&1)
sum+=a[now+1],count++;
j>>=1;
now++;
}
if (abs(sum)<ans)
{
ans=abs(sum);
cnt=count;
}
else if (abs(sum)==ans) cnt=min(cnt,count);
if (mp[sum])
mp[sum]=min(mp[sum],count);
else
mp[sum]=count;
}
for (int i=1,j,now,count;i<(1<<(n-n/2));i++)
{
j=i;
sum=0;
count=0;
now=0;
while (j)
{
if (j&1)
sum+=a[now+n/2+1],count++;
j>>=1;
now++;
}
if (abs(sum)<ans)
{
ans=abs(sum);
cnt=count;
}
else if (abs(sum)==ans) cnt=min(cnt,count);
qwq=mp.lower_bound(-sum);
ll nw;
if (qwq!=mp.end())
{
nw=sum+qwq->first;
nw=abs(nw);
if (nw<ans)
{
ans=nw;
cnt=qwq->second+count;
}
else if (nw==ans) cnt=min(cnt,qwq->second+count);
}
if (qwq!=mp.begin())
{
qwq--;
nw=sum+qwq->first;
nw=abs(nw);
if (nw<ans)
{
ans=nw;
cnt=qwq->second+count;
}
else if (nw==ans) cnt=min(cnt,qwq->second+count);
}
}
printf("%lld %d\n",ans,cnt);
}
return 0;
}
[poj] 3977 Subset || 折半搜索MITM的更多相关文章
- POJ 3977 Subset | 折半搜索
题目: 给出一个整数集合,求出非空子集中元素和绝对值最小是多少(元素个数尽量少) 题解: 分成两半 爆搜每一半,用map维护前一半的值 每搜出后一半的一个值就去map里找和他和绝对值最小的更新答案 # ...
- POJ 3977 - subset - 折半枚举
2017-08-01 21:45:19 writer:pprp 题目: • POJ 3977• 给定n个数,求一个子集(非空)• 使得子集内元素和的绝对值最小• n ≤ 35 AC代码如下:(难点:枚 ...
- POJ 3977 Subset(折半枚举+二分)
SubsetTime Limit: 30000MS Memory Limit: 65536KTotal Submissions: 6754 Accepted: 1277 D ...
- poj 3977 Subset(折半枚举+二进制枚举+二分)
Subset Time Limit: 30000MS Memory Limit: 65536K Total Submissions: 5721 Accepted: 1083 Descripti ...
- 【折半枚举+二分】POJ 3977 Subset
题目内容 Vjudge链接 给你\(n\)个数,求出这\(n\)个数的一个非空子集,使子集中的数加和的绝对值最小,在此基础上子集中元素的个数应最小. 输入格式 输入含多组数据,每组数据有两行,第一行是 ...
- POJ - 3977 Subset(二分+折半枚举)
题意:有一个N(N <= 35)个数的集合,每个数的绝对值小于等于1015,找一个非空子集,使该子集中所有元素的和的绝对值最小,若有多个,则输出个数最小的那个. 分析: 1.将集合中的元素分成两 ...
- POJ 3977 Subset
Subset Time Limit: 30000MS Memory Limit: 65536K Total Submissions: 3161 Accepted: 564 Descriptio ...
- POJ3977:Subset——题解(三分+折半搜索)
http://poj.org/problem?id=3977 题目大意:有一堆数,取出一些数,记他们和的绝对值为w,取的个数为n,求在w最小的情况下,n最小,并输出w,n. ————————————— ...
- bzoj2679: [Usaco2012 Open]Balanced Cow Subsets(折半搜索)
2679: [Usaco2012 Open]Balanced Cow Subsets Time Limit: 10 Sec Memory Limit: 128 MBSubmit: 462 Solv ...
随机推荐
- 【杂题总汇】HDU多校赛第十场 Videos
[HDU2018多校赛第十场]Videos 最后一场比赛也结束了…… +HDU传送门+ ◇ 题目 <简要翻译> 有n个人以及m部电影,每个人都有一个快乐值.每场电影都有它的开始.结束时间和 ...
- elasticsearch-dsl笔记
一.elasticsearch安装 安装java1.8以上 安装elasticsearch-rtf(https://github.com/medcl/elasticsearch-rtf) head插件 ...
- JDK1.8简单配置环境变量---两步曲
鄙人最近重新装完系统之后,在安装和配置jdk1.8的时候,发现网上许多教程配置jdk环境变量时都还在沿用传统的方式配置,但是随着技术的更新,完全没有必要那么麻烦了. 下载和安装jdk的教程,在这里就不 ...
- vue数据绑定html
html标签的纯文本显示/被当做html标签处理: 1)使用两个大括号时,假如字符串内容是html标签,那么不会被转义: 2)使用三个大括号时,字符串内的html标签会被直接转义 a.两个大括号: & ...
- tp5.0初入
1.目录结构 |-application 应用目录 是整个网站的核心 |---|---index 前台目录 |---|-----|---controller 控制器 |---|-----|---mod ...
- 笔记-redis安装
笔记-redis安装配置 1. redis安装配置 1.1. windows环境安装 win8已有redis 查看版本:redis-server –version 想更新到5.0.0, ...
- Android面试收集录15 Android Bitmap压缩策略
一.为什么Bitmap需要高效加载? 现在的高清大图,动辄就要好几M,而Android对单个应用所施加的内存限制,只有小几十M,如16M,这导致加载Bitmap的时候很容易出现内存溢出.如下异常信息, ...
- Dragger 2遇到的坑 Dragger2详解 Dragger2学习最好的资料
我是曹新雨,我为自己代言.现在的菜鸟,3年以后我就是大神.为自己加油.微信:aycaoxinyu Dragger2是什么,我就不再说了.资料一堆,而且里面的注解什么意思,我推荐两篇文章,这两篇都是我精 ...
- python 发送 get post请求
GET请求: python2.7: import urllib,urllib2 url='http://192.168.199.1:8000/mainsugar/loginGET/' textmod ...
- 洛谷P1331 海战
海战 题目链接 这还是一道联通块的题,只是需要判断是否存在以下四种情况: o. .o oo oo oo oo o. .o 如果存在就是Bad placement. 要注意标记以下,不然会出现多次输出B ...