Sequence(Poj2442)

题意:

有m个数列,每个数列n个值,每个序列中选取一个值可以组成n^m种不同的序列,求前n小的序列和。

Input

1
2 3
1 2 3
2 2 3

Output

3 3 4

分析:

用两个优先队列维护前n小和。首先将第一列n个数字放入从大到小的优先队列中,每次弹出一个最小值和下一行的每个元素相加,并放入另一个从小到大的优先队列中,当放满n个值时,每次求和结果先和队列中的top对比,若小于top则弹出并塞入这个和,否则舍弃这个较大和。这样维护的就是求和到第i行时的前n小序列和。当数列中n个元素都和下一列的元素求和完后,将这些前n小和又倒出来塞入从大到小的队列中,这样就和一开始对第一行的数列一样,每次选取一个最小值进行和后面的值求和,并将和塞入从小到大的优先队列中,这样反复倒腾最后加和到最后一行时仍然是所有数列求和的最小值,然后放入从大到小的数列中,依次弹出即是升序输出。


• 两组两组的看,首先要排序,然后从头开始找最小的N个和。

• 怎么找是个问题,对于第一组我们取i=1,第二组取j=1,然后a[1]+b[1]肯定是最小的,然后a[2]+b[1],a[1]+b[2]进入候选项,如果我们下一次选中了a[2]+b[1],那么我们又要将a[3]+b[1],a[2]+b[2]加入候选项。

• 但是我们要保证产生候选项不能重复,比如a[1]+b[2]和a[2]+b[1]都可以产生a[2]+b[2],所以我们要排除其中的一种,也就是说,我们要将候选项的下标计算变得有限制。

• 候选项的下标都是通过选中当前项的下标加一得到的,那么为了避免重复,我们要制定一种规则。假如规定为如果j+1,那么这个候选项被选中的时候i就不能更新。

  1. i=1,j=1

• 更新i=2,j=1, flag = true

• 更新i=1, j=2, flag = false

  1. 假如选中i=2,j=1,flag = true

• 由于是true,可以更新i=3,j=1,flag = true

• 更新i=2,j=2,flag = false

  1. 假如选中i=1,j=2,flag = false

• 由于false,不能更新i

• 更新i=1,j=3,flag = false

......

对于两个序列我们就可以a[0]+b[0],a[1]+b[0]一直到a[n-1]+b[0],然后是依次加a[1],这样我们就可以得到一个新的序列,如果只有两个序列,那我们的序列就是符合条件的,如果对于三个序列那就是两个序列组成的新序列看成新的a序列,第三个序列就是b序列,想一想,是不是?

这样依次迭代,到最后就是所求的m个序列组成的新序列,如果我们全部暴力存储,显然时间和空间开销都是非常大的,到最后跟直接m个序列暴力是没有区别的,达到n^m。 每次维护长为n的数组就可以啦



#include<stdio.h>///两个优先队列组合使用
#include<queue>
using namespace std;
int main()
{
int t,i,j,m,n,num;
scanf("%d",&t);
while(t--)
{
scanf("%d%d",&m,&n);
priority_queue<int ,vector<int>,less<int> >s;///一个优先级 从 小->大
priority_queue<int ,vector<int>,greater<int> >q;///一个优先级 从 大->小
for(i=1; i<=m; i++)///输入m列
{
if(i==1)///先将第一列作为基础塞入q队列中
{
for(j=0; j<n; j++)
{
scanf("%d",&num);
q.push(num);
}
}
else
{
int numd[n+10],sum;
for(j=0; j<n; j++)///几列,存入一个数组中
{
scanf("%d",&numd[j]);
}
while(q.size())///从q队列中,一个一个选出元素,分别与后面输入的数组中的每一个值相加
{
sum=q.top();///选出队首元素,记为sum
q.pop();///出列
for(j=0; j<n; j++)///和输入的数组中每个都加一遍
{
if(s.size()==n&&s.top()>sum+numd[j])///若超过或等于了n个元素,判断s队列中的队首(放入队列中的最大值)是否大于当前选出的数和数组中元素之和
{
s.pop();///若大于,弹出那个较大数,重新塞入求和而得的较小的数
s.push(sum+numd[j]);
}
else if(s.size()<n)///s队列中若没达到n个元素,加完就塞进去
{
s.push(sum+numd[j]);
}
}///这样一个循环下来,就将下一组数与当前q队列中的某一个元素相加完毕,并筛选出了前n个较小的求和数
}///while的下一轮将求和队列中的下一个数,并继续筛选求和数中的前n小值
while(s.size())///所有数筛选完毕此时在s队列中都是最小的前n个数
{
q.push(s.top());
s.pop();
}///每行完成更新后将求和结果统一塞回Q队列中准备下一行筛选求和
}
}
while(q.size())
{
printf("%d%c",q.top(),(q.size()-1==0)?'\n':' ');
q.pop();
}
}
return 0;
}

 

Sequence(Poj2442)的更多相关文章

  1. POJ2442 Sequence(堆的骚操作)

    Description Given m sequences, each contains n non-negative integer. Now we may select one number fr ...

  2. POJ-2442 Sequence K路归并问题

    题目链接:http://poj.org/problem?id=2442 问题一:K个有序表合成一个有序表,元素共有n个.用堆优化 问题二:两个序列的前n小的元素.堆优化. 这题就是问题二的扩展,每次处 ...

  3. POJ2442 Sequence

    题目链接. #include <iostream> #include <cstdio> #include <cstring> #include <cstdli ...

  4. POJ2442:Sequence

    浅谈堆:https://www.cnblogs.com/AKMer/p/10284629.html 题目传送门:http://poj.org/problem?id=2442 我们先简化题意,假设只有两 ...

  5. $POJ2442\ Sequence$ 堆

    正解:堆 解题报告: 传送门$QwQ$ 全场除了我都切了系列$kk$ 首先看$n=2$的情况. 首先暴力不说?就记录一个$sum$再分别记录$xy$两维的下标存到堆里面每次取队头并继续扩展就完事$Qw ...

  6. oracle SEQUENCE 创建, 修改,删除

    oracle创建序列化: CREATE SEQUENCE seq_itv_collection            INCREMENT BY 1  -- 每次加几个              STA ...

  7. Oracle数据库自动备份SQL文本:Procedure存储过程,View视图,Function函数,Trigger触发器,Sequence序列号等

    功能:备份存储过程,视图,函数触发器,Sequence序列号等准备工作:--1.创建文件夹 :'E:/OracleBackUp/ProcBack';--文本存放的路径--2.执行:create or ...

  8. DG gap sequence修复一例

    环境:Oracle 11.2.0.4 DG 故障现象: 客户在备库告警日志中发现GAP sequence提示信息: Mon Nov 21 09:53:29 2016 Media Recovery Wa ...

  9. Permutation Sequence

    The set [1,2,3,-,n] contains a total of n! unique permutations. By listing and labeling all of the p ...

随机推荐

  1. JVM 第一篇:编译 OpenJdk14 ,我行你也行

    本文内容过于硬核,建议有 Java 相关经验人士阅读. 1 引言 从上周开始一直在看周志明的 「深入理解Java虚拟机:JVM高级特性与最佳实践(第3版)」 ,好多年之前看过第二版的,绝对算的上是国内 ...

  2. Docker 部署 redis教程,附带部分小建议,防止踩坑

    Docker 部署 redis,附带部分小建议,防止踩坑 跟所有人一样,我们先从docker基本命令开始 一.拉取redis镜像(配图来自菜鸟,其实截图没多大意义,对比看下) # 默认就拉取laste ...

  3. Spring_mybatis结合之1.1

    Spring和mybatis结合,Spring管理容器,连接数据库等,mybatis负责管理sql语句,sql的入参和出参等 三种方法: 1.原始dao开发(不怎么用,好奇的宝宝可以自己搜搜.是dao ...

  4. unimrcp plugin 分析

    摘要: unimrcp 访问媒体资源是通过插件实现,社区的代码给出了demo plugin,但是距离一个生产插件还是有一段的距离.这边文章介绍插件的整个逻辑过程,以及如何实现我们自己的插件.

  5. Python中的协程,为什么说它的底层是生成器?

    我们曾经在golang关于goroutine的文章当中简单介绍过 协程 的概念,我们再来简单review一下.协程又称为是微线程,英文名是Coroutine.它和线程一样可以调度,但是不同的是线程的启 ...

  6. Python面向对象中的self到底是什么?

    初次接触类的概念,在学习的网页上,对self的解释是self是方法的一个参数,在方法调用的时候,这个参数是默认传参数的我们看一个例子 很多人学习python,不知道从何学起.很多人学习python,掌 ...

  7. webpack打包初始入门教程

    Webpack 是一个前端资源加载/打包工具.它将根据模块的依赖关系进行静态分析,然后将这些模块按照指定的规则生成对应的静态资源. 从图中我们可以看出,Webpack 可以将多种静态资源 js.css ...

  8. Currency Exchange(SPFA判负环)

    Several currency exchange points are working in our city. Let us suppose that each point specializes ...

  9. 类文件的结构、JVM 的类加载过程、类加载机制、类加载器、双亲委派模型

    一.类文件的结构 我们都知道,各种不同平台的虚拟机,都支持 "字节码 Byte Code" 这种程序存储格式,这构成了 Java 平台无关性的基石.甚至现在平台无关性也开始演变出 ...

  10. Activiti7 流程变量(理论)

    什么是流程变量 流程变量在Activiti中是一个非常重要的角色,流程运转有时需要靠流程变量,业务系统和Activiti结合时少不了流程变量,流程变量就是Activiti在管理工作流时根据管理需要而设 ...