Sort---hdu5884(优先队列+二分)
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5884
题意:有n个有序序列,每个序列有ai个元素,现在有一个程序每次可以归并最多k个序列,最终把所有的序列合并成一个,每次归并所需要的代价是所有序列的长度和;
现有一个代价界限T,就是总的代价不能超过T,求符合条件的最小的K;
当给定一个K的准确值时,我们可以每次选择最小的k个数进行合并;所以我们可以用优先队列来处理,但是由于范围比较大,可以优化一下,只让合并形成的序列进入优先队列,每次取数组和队列中较小的一个即可;
对于k可以用二分的方法来求,但是会发现当n=5,k=4的时候,当直接运用上面的做法,最后没有k个数,那么就不能保证单调性了,为了保证每次都是k个序列进行合并,我们可以运用补0的方法进行处理,这样就保证了二分的正确性;
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<iostream>
#include<vector>
#include<queue>
#include<set>
using namespace std;
#define met(a, b) memset(a, b, sizeof(a))
#define N 100005
#define INF 0x3f3f3f3f
typedef long long LL; int M, n, a[N], sum[N]; bool Judge(int k)
{
int r = (n-k)%(k-), Index;
LL s;
if(r == )///如果已经满足每次都是k个数了,直接取数组的前k项即可;
{
s = sum[k];
Index = k+;
}
else///否则就先把前r+1个数进行合并;
{
s = sum[r+];
Index = r+;
}
priority_queue<LL>Q;
Q.push(s); while(!Q.empty() || Index <= n)
{
if(Index > n && Q.size() == ) break;///当只剩下队列中的一个数时,说明已经合并完成了; int cnt = ; LL part = ;
while(cnt<k && (!Q.empty() || Index<=n))
{
if(Index <=n && (Q.empty() || a[Index] <= Q.top()))
part += a[Index++];
else
{
part += Q.top();
Q.pop();
}
cnt++;
}
s += part;
if(s > M) break; Q.push(part);
}
return s<=M;
} int main()
{
int T;
scanf("%d", &T);
while(T--)
{
met(a, );
met(sum, ); scanf("%d %d", &n, &M); for(int i=; i<=n; i++)
scanf("%d", &a[i]); sort(a, a+n+);
for(int i=; i<=n; i++)
sum[i] = sum[i-] + a[i]; int L = , R = n, ans = ;
while(L <= R)
{
int Mid = (L+R)/;
if(Judge(Mid))
{
R = Mid - ;
ans = Mid;
}
else
L = Mid + ;
}
printf("%d\n", ans);
}
return ;
}
/*
5 15
0 0 0 0 0
*/
Sort---hdu5884(优先队列+二分)的更多相关文章
- Sort HDU5884(二分+多叉哈夫曼树)
HDU5884 Sort 题意:有n个序列要进行归并,每次归并的代价是两个序列的长度的和,要求最终的代价不能超过规定的T,求在此前提下一次能同时进行归并的序列的个数k. 思路:还是太单纯,看完题目一直 ...
- Sort HDU - 5884(优先队列+二分)
Sort Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
- POJ 2010 Moo University - Financial Aid( 优先队列+二分查找)
POJ 2010 Moo University - Financial Aid 题目大意,从C头申请读书的牛中选出N头,这N头牛的需要的额外学费之和不能超过F,并且要使得这N头牛的中位数最大.若不存在 ...
- sort()和优先队列的总结
一.关于sort函数 sort()排序函数默认是从小到大, a={5,3,2,1,6 }; sort(a,a+n); //输出是1 2 3 5 6 这里如果要从到小排序,则有两种方式可以满足 (1) ...
- Sort(hdu5884)
Sort Time Limit: 3000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)Total Submis ...
- sort排序与二分查找
#include<iostream> #include<vector> #include<algorithm> #include<string> usi ...
- 给小班讲stl 之 map、sort、优先队列
引子:最近老师让给小班讲课,讲stl,,但是我觉得就小班现在这水平根本讲不懂好不好,,,,
- Gym 101064 D Black Hills golden jewels (二分)
题目链接:http://codeforces.com/gym/101064/problem/D 问你两个数组合相加的第k大数是多少. 先sort数组,二分答案,然后判断其正确性(判断过程是枚举每个数然 ...
- 4 Values whose Sum is 0(二分)
4 Values whose Sum is 0 Time Limit: 15000MS Memory Limit: 228000K Total Submissions: 21370 Accep ...
随机推荐
- Codeforces Round #213 (Div. 2) A. Good Number
#include <iostream> #include <vector> using namespace std; int main(){ ; cin >> n ...
- MyEclipse 10 之下Web Service 的创建和实现
(一)Web service服务端开发 1. 新建一个Web service project, 菜单New -> Web Service Project, 2. 新建一个 Java Bean, ...
- mysql 动态sql语句
; SET @ss = ' INSERT INTO prod_attr SELECT ? AS prod_id,A.* FROM ( SELECT 1 AS attr_id,\'中国出版社\' AS ...
- Oracle 10g安装64位图解流程
1. 安装准备阶段 1.1 安装Oracle环境 本例使用X-Manager来实现与Linux系统的连接,本例使用的所有命令和操作都是在X-Manager下进行.X-Manager安装完成后的配置方法 ...
- python多线程使用
内容链接: http://www.liaoxuefeng.com/wiki/001374738125095c955c1e6d8bb493182103fac9270762a000/00138683236 ...
- 实现Fragment 切换时不重新实例化
以前实现Fragment的切换都是用replace方法实现 public void startFragmentAdd(Fragment fragment) { FragmentManager frag ...
- 一些Discuz!代码
首行缩进2字符 [code][p=20, 2, left]首行缩进2字符[/p][/code]
- Unity中的协程(一)
这篇文章很不错的问题,推荐阅读英文原版: Introduction to Coroutines Scripting with Coroutines 这篇文章转自:http://blog.csdn. ...
- linux下利用curl监控网页shell脚本
#!/bin/bash smail() {mail -s "$1" gjw_apparitor@gmail.com <<EOF$1$2====report time: ...
- IN()
High Performance My SQL, Third Edition Consider the followingWHERE clause: WHERE eye_color IN('brown ...