输入一个长度为 n 的整数数列,从小到大输出前 m 小的数。
输入格式
第一行包含整数 n 和 m。
第二行包含 n 个整数,表示整数数列。
输出格式
共一行,包含 m 个整数,表示整数数列中前 m 小的数。
数据范围
1≤m≤n≤105,
1≤数列中元素≤109
输入样例:
5 3
4 5 1 3 2
输出样例:
1 2 3
down和up是针对的某个点,我看视频的时候光理解原理了,没注意down和up的细节
就是y总讲的特别长,希望刚开始看这个课的人不要像我一样晕乎乎的
!!!!!!!!!!!!!!!!!!!
为什么是从n/2开始down呢,假设共有7个数,也就是三层,7 / 2 = 3 , 也就是从3那个点 开始down,一直down到1,所以就是全部的数都被作用到了,实在是 女少 啊。
然后就是让最后一位的值赋给h【1】,删除最后一个下标,然后让根节点一直往下down,在输出一次最小值也就是根节点的时候,把根节点删除
看代码!
#include<iostream>
#include<algorithm>
using namespace std ;
const int N = 1e5;
int n, m ;
int sz , q[N];
void down(int u)
{
cin.tie(0);
int t = u ;
if( u * 2 <= sz && q[u*2] < q[t] )t = u * 2 ;
if(u * 2 + 1 <= sz && q[u*2 + 1] < q[t])t = u * 2 + 1 ;
if(u!=t)
{
swap(q[t] , q[u]);
down(t);
}
}
int main()
{
cin >> n >> m;
for(int i = 1 ; i <= n ; i++) cin >> q[i];
sz = n ;
for(int i = n / 2 ; i ; i--) down(i) ;
while(m--)
{
cout << q[1] << " ";
q[1] = q[sz] ;
sz--;
down(1);
}
return 0 ;
}