记录一个求动态中位数的方法
对顶堆口诀
1.逆序交换
2.下多转移
P1168 中位数https://www.luogu.com.cn/problem/P1168
#include <iostream>
#include <cstring>
#include <algorithm>
#include <sstream>
#include <cmath>
#include <queue>
#include <vector>
#include <map>
#include<set>
using namespace std;
typedef long long ll;
#define int long long
#define endl '\n'
#define lowbit(x) x &(-x)
#define mh(x) memset(x, -1, sizeof h)
#define debug(x) cerr << #x << "=" << x << endl;
#define brk exit(0);
const int N = 2e5 + 10;
const int mod = 998244353;
const double esp = 1e-6;
const double pi = acos(-1);
inline int read()
{
register int x = 0, f = 1;
register char c = getchar();
while (c < '0' || c > '9')
{
if (c == '-')
f = -1;
c = getchar();
}
while (c >= '0' && c <= '9')
x = (x << 3) + (x << 1) + (c ^ 48), c = getchar();
return x * f;
}
inline void write(register int x)
{
if (x > 9)
write(x / 10);
putchar(x % 10 + '0');
}
int a[N], b[N];
multiset<int> s;
void solve()
{
priority_queue<int> l;
priority_queue<int,vector<int>,greater<int>> r;
int n;
cin >> n;
for (int i = 1; i <= n;i++)
{
int x;
cin >> x;
if(l.empty()||x<=l.top())
l.push(x);
else
r.push(x);
if(l.size()>r.size()+1)
r.push(l.top()), l.pop();
if(r.size()>l.size())
l.push(r.top()),r.pop();
if(i&1)
cout << l.top() << endl;
}
}
signed main()
{
cin.tie(0)->sync_with_stdio(0);
int T = 1;
//cin >> T;
while (T--)
{
solve();
}
return 0;
}
另一个方法是对一个数组不断扩展,用二分找到插入的位置,这样每次数组均为有序的,直接输出中间位置即可。复杂度O(nlogn*insert函数复杂度)
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define int long long
#define endl '\n'
#define lowbit(x) x &(-x)
#define mh(x) memset(x, -1, sizeof h)
#define debug(x) cerr << #x << "=" << x << endl;
#define brk exit(0);
const int N = 2e5 + 10;
const int mod = 998244353;
const double esp = 1e-6;
const double pi = acos(-1);
//unordered_map<int, unordered_map<int, int>> table;
void solve()
{
int n;
cin >> n;
vector<int> vec,a(n+1);
for (int i = 1; i <= n;i++)
cin >> a[i];
// vec.push_back(a[1]);
// cout << a[1] << endl;
for (int i = 1;i<=n;i++)
{
auto it = upper_bound(vec.begin(), vec.end(), a[i]);
vec.insert(it, a[i]);
if(i&1)
cout << vec[vec.size()/2]<<endl;
}
}
signed main()
{
cin.tie(0)->sync_with_stdio(0);
int T = 1;
//cin >> T;
while (T--)
{
solve();
}
return 0;
}