w5 P1631 序列合并
主要思路:由于题干中说明给出的两个序列是单调不降的,所以不需要再对序列进行一个排序。这里其实有一点贪心的意思但不完全是贪心算法。首先把两个序列分别放入两个数组,然后进行各个元素和的遍历。构建一个优先序列pq,优先序列会对里面的元素自动降序排列,每次遍历都判断和是否小于pq 内的最大元素,即pq.top(),是则扔出top,放入当前的和。
以样例为例:
a:a1=2 a2=6 a3=6
b:b1=1 b2=4 b3=8
若pq大小!=N,则先把元素放入pq,pq:10 6 3,分别对应a1+b1 a1+b2 a1+b3
a2+b1=7<10,扔出10,放入7,pq:7 6 3
a2+b2=10>7,继续遍历
a2+b3=14>7,继续遍历
a3+b1=7==7,继续遍历
a3+b2=10>7,继续遍历
a3+b3=14>7,已全部遍历完,倒序输出结果
代码如下:
#include<iostream>
#include<queue>
using namespace std;
int N,a[100005],b[100005],cnt;
priority_queue<int> pq;
int main()
{
cin>>N;
for(int i=0;i<N;++i) cin>>a[i];
for(int i=0;i<N;++i) cin>>b[i];
for(int i=0;i<N;++i){
for(int j=0;j<N;++j){
if(pq.size()<N){ //若pq大小!=N时输入数据
pq.push(a[i]+b[j]);
}
else{ //pq大小==N时,判断当前数字,比top大则继续循环,比top小则放入pq
if(a[i]+b[j]<pq.top()){
pq.pop();
pq.push(a[i]+b[j]);
}
else break;
}
}
}
int ans[N],i=N-1;
while(!pq.empty()){ //倒叙存放结果
ans[i]=pq.top();
pq.pop();
i--;
}
for(int i=0;i<N;++i) cout<<ans[i]<<" "; //输出结果
cout<<endl;
return 0;
}