博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
【poj 3977】Subset (折半枚举)
阅读量:5044 次
发布时间:2019-06-12

本文共 1274 字,大约阅读时间需要 4 分钟。

#include 
#include
#include
#include
#include
using namespace std;#define ll long long#define P pair
ll a[40];P p[1 << 20];ll Abs(ll x) { if (x >= 0) return x; return -x;}int main() { int n; while (scanf("%d", &n) != EOF && n) { for (int i = 0; i < n; i++) scanf("%lld", &a[i]); int rn = n / 2; P res; res = {Abs(a[0]), 1}; for (int i = 1; i < 1 << rn; i++) { p[i] = { 0, 0}; for (int j = 0; j < rn; j++) { if (i >> j & 1) { p[i].first += a[j]; p[i].second++; } } //只在p[]中取数 res = min(res, P(Abs(p[i].first), p[i].second)); } sort(p + 1, p + (1 << rn)); //去重 int m = 2; for (int i = 2; i < 1 << rn; i++) { if (p[m - 1].first < p[i].first) p[m++] = p[i]; } for (int i = 1; i < 1 << (n - rn); i++) { ll tmp = 0; int tnum = 0; for (int j = 0; j < n - rn; j++) { if (i >> j & 1) { tmp += a[j + rn]; tnum++; } } //不在p[]取数 res = min(res, P(Abs(tmp), tnum)); int pos = lower_bound(p + 1, p + m, P(-tmp, 0)) - p; for (int j = -1; j <= 0; j++) { if (j + pos < 1 || j + pos >= m) continue; res = min(res, P(Abs(tmp + p[pos + j].first), tnum + p[pos + j].second)); } } printf("%lld %d\n", res.first, res.second); }}

 

转载于:https://www.cnblogs.com/hs-zlq/p/11230696.html

你可能感兴趣的文章
OAuth和OpenID的区别
查看>>
android 分辨率自适应
查看>>
查找 EXC_BAD_ACCESS 问题根源的方法
查看>>
国外媒体推荐的5款当地Passbook通行证制作工具
查看>>
日常报错
查看>>
list-style-type -- 定义列表样式
查看>>
hibernate生成表时,有的表可以生成,有的却不可以 2014-03-21 21:28 244人阅读 ...
查看>>
mysql-1045(28000)错误
查看>>
Ubuntu 编译出现 ISO C++ 2011 不支持的解决办法
查看>>
1.jstl c 标签实现判断功能
查看>>
Linux 常用命令——cat, tac, nl, more, less, head, tail, od
查看>>
超详细的Guava RateLimiter限流原理解析
查看>>
VueJS ElementUI el-table 的 formatter 和 scope template 不能同时存在
查看>>
Halcon一日一练:图像拼接技术
查看>>
Swift - RotateView
查看>>
iOS设计模式 - 中介者
查看>>
centos jdk 下载
查看>>
HDU 1028 Ignatius and the Princess III(母函数)
查看>>
(转)面向对象最核心的机制——动态绑定(多态)
查看>>
token简单的使用流程。
查看>>