题目链接
题意:给定一序列
{
a
1
,
a
2
,
a
3
,
.
.
.
,
a
n
}
\{a_1,a_2,a_3,...,a_n\}
{a1,a2,a3,...,an},问该序列所有长度为
i
i
i的子序列的最大公共元素是多少(
i
=
1
,
2
,
.
.
.
,
n
i=1,2,...,n
i=1,2,...,n)
思路:我们注意到:对于某个数字,我们需要考虑区间至少要多大才可以每个区间都包含到它。因此我们维护对于每种数字,其与下一个同种数字的最大距离,同时考虑元素到头和到尾的距离。如此一来就可以知道对于每种数字最短需要多大的区间。之后只要先
(
a
n
s
[
d
i
s
[
数
字
种
类
]
]
=
m
i
n
(
a
n
s
[
d
i
s
[
数
字
种
类
]
]
,
数
字
种
类
)
)
(ans[dis[数字种类]]=min(ans[dis[数字种类]],数字种类))
(ans[dis[数字种类]]=min(ans[dis[数字种类]],数字种类)),接着维护答案序列的最小值前缀即可。
#include <bits/stdc++.h>
#define pcc pair<char, char>
#define pii pair<int, int>
#define vi vector<int>
#define vl vector<ll>
#define rep(i, x, y) for (int i = x; i < y; i++)
#define per(i, x, y) for (int i = x; i >= y; i--)
#define rep0(i, n) for (int i = 0; i < (n); i++)
#define per0(i, n) for (int i = (n)-1; i >= 0; i--)
#define mp make_pair
#define pb push_back
#define F first
#define S second
#define sz(x) (x).size()
#define all(x) (x).begin(), (x).end()
#define ll long long
#define ull unsigned long long
#define db double
#define ld long double
using namespace std;
inline int read() {
int x = 0, f = 1;
char ch = getchar();
while (ch < '0' || ch > '9') {
if (ch == '-') f = -1;
ch = getchar();
}
while (ch >= '0' && ch <= '9') {
x = x * 10 + ch - '0';
ch = getchar();
}
return x * f;
}
const double eps = 1e-9;
const int inf = 0x3f3f3f3f;
const int mod = 1e9 + 7;
const int maxn = 3e5 + 10;
/***************main****************/
ll T = 1;
ll m, n;
ll a[maxn], prv[maxn], dis[maxn], ans[maxn], last[maxn];
int main() {
T = read();
while (T--) {
cin >> n;
rep(i, 1, n + 1) a[i] = read();
rep(i, 0, n + 1) ans[i] = dis[i] = prv[i] = last[i] = 0;
rep(i, 1, n + 1) ans[i] = inf;
rep(i, 1, n + 1) {
dis[a[i]] = max(dis[a[i]], i - prv[a[i]]);
last[a[i]] = i;
prv[a[i]] = i;
}
rep(i, 1, n + 1) if (last[i]) dis[i] = max(dis[i], n + 1 - last[i]);
rep(i, 1, n + 1) ans[dis[i]] = min(ans[dis[i]], i * 1ll);
rep(i, 2, n + 1) ans[i] = min(ans[i], ans[i - 1]);
rep(i, 1, n + 1) cout << (ans[i] == inf ? -1 : ans[i]) << ' ';
cout << '\n';
}
return 0;
}