E2. Three Blocks Palindrome (hard version)

The only difference between easy and hard versions is constraints.

You are given a sequence aa consisting of nn positive integers.

Let's define a three blocks palindrome as the sequence, consisting of at most two distinct elements (let these elements are aa and bb, aa can be equal bb) and is as follows: [a,a,…,ax,b,b,…,by,a,a,…,ax][a,a,…,a⏟x,b,b,…,b⏟y,a,a,…,a⏟x]. There x,yx,y are integers greater than or equal to 00. For example, sequences [][], [2][2], [1,1][1,1], [1,2,1][1,2,1], [1,2,2,1][1,2,2,1] and [1,1,2,1,1][1,1,2,1,1] are three block palindromes but [1,2,3,2,1][1,2,3,2,1], [1,2,1,2,1][1,2,1,2,1] and [1,2][1,2] are not.

Your task is to choose the maximum by length subsequence of aa that is a three blocks palindrome.

You have to answer tt independent test cases.

Recall that the sequence tt is a a subsequence of the sequence ss if tt can be derived from ss by removing zero or more elements without changing the order of the remaining elements. For example, if s=[1,2,1,3,1,2,1]s=[1,2,1,3,1,2,1], then possible subsequences are: [1,1,1,1][1,1,1,1], [3][3] and [1,2,1,3,1,2,1][1,2,1,3,1,2,1], but not [3,2,3][3,2,3] and [1,1,1,1,2][1,1,1,1,2].

Input

The first line of the input contains one integer tt (1≤t≤1041≤t≤104) — the number of test cases. Then tt test cases follow.

The first line of the test case contains one integer nn (1≤n≤2⋅1051≤n≤2⋅105) — the length of aa. The second line of the test case contains nn integers a1,a2,…,ana1,a2,…,an (1≤ai≤2001≤ai≤200), where aiai is the ii-th element of aa. Note that the maximum value of aiai can be up to 200200.

It is guaranteed that the sum of nn over all test cases does not exceed 2⋅1052⋅105 (∑n≤2⋅105∑n≤2⋅105).

Output

For each test case, print the answer — the maximum possible length of some subsequence of aa that is a three blocks palindrome.

Example
input
Copy
6
8
1 1 2 2 3 2 1 1
3
1 3 3
4
1 10 10 1
1
26
2
2 1
3
1 1 1
output
Copy
7
2
4
1
1
3

 用1—200之间的数分别作两边,前缀和加暴力

 用长整型开数组会翻车

#include <iostream>
#include <vector>
#include <algorithm>
#include <string>
#include <set>
#include <queue>
#include <map>
#include <sstream>
#include <cstdio>
#include <cstring>
#include <numeric>
#include <cmath>
#include <iomanip>
#include <deque>
#include <bitset>
//#include <unordered_set>
//#include <unordered_map>
#define ll              long long
#define pii             pair<int, int>
#define rep(i,a,b)      for(int  i=a;i<=b;i++)
#define dec(i,a,b)      for(int  i=a;i>=b;i--)
#define forn(i, n)      for(int i = 0; i < int(n); i++)
using namespace std;
int dir[4][2] = { { 1,0 },{ 0,1 } ,{ 0,-1 },{ -1,0 } };
const long long INF = 0x7f7f7f7f7f7f7f7f;
const int inf = 0x3f3f3f3f;
const double pi = 3.14159265358979323846;
const double eps = 1e-6;
const int mod = 1e9 + 7;
const int N = 3e3 + 5;
//if(x<0 || x>=r || y<0 || y>=c)

inline ll read()
{
    ll x = 0; bool f = true; char c = getchar();
    while (c < '0' || c > '9') { if (c == '-') f = false; c = getchar(); }
    while (c >= '0' && c <= '9') x = (x << 1) + (x << 3) + (c ^ 48), c = getchar();
    return f ? x : -x;
}
ll gcd(ll m, ll n)
{
    return n == 0 ? m : gcd(n, m % n);
}
ll lcm(ll m, ll n)
{
    return m * n / gcd(m, n);
}
bool prime(int x) {
    if (x < 2) return false;
    for (int i = 2; i * i <= x; ++i) {
        if (x % i == 0) return false;
    }
    return true;
}
ll qpow(ll m, ll k, ll mod)
{
    ll res = 1, t = m;
    while (k)
    {
        if (k & 1)
            res = res * t % mod;
        t = t * t % mod;
        k >>= 1;
    }
    return res;
}
bool check(string s,string s1)
{
    int cnt = 0;
    forn(i, s.size())
    {
        if (s[i] != s1[i])
            cnt++;
    }
    if (cnt > 1)
        return false;
    return true;
}
int main()
{
    int T;
    cin >> T;
    while (T--)
    {
        int n;
        cin >> n;
        vector<int> a(n + 1);
        rep(i, 1, n)
            cin >> a[i];
        vector<vector<int>> dp(n + 1, vector<int>(205)),pos(205);
        rep(i, 1, n)
        {
            dp[i] = dp[i - 1];
            dp[i][a[i]]++;
            pos[a[i]].push_back(i);
        }
        int res = 1;
        rep(i, 1, 200)
        {
            forn(k, pos[i].size()/2)
            {
                int sz = pos[i].size(), y = 0;
                int l = pos[i][k], r = pos[i][sz - k - 1]-1;
                rep(j, 1, 200)
                {
                    y = max(dp[r][j] - dp[l][j], y);
                }
                res = max(res, (k+1) * 2 + y);
            }
        }
        cout << res << endl;
    }
    return 0;
}

 

posted @ 2020-06-26 10:06  DeaL57  阅读(218)  评论(0)    收藏  举报