求最长上升自序列,注意算法复杂度得O(nlogn)。
/*
* Author: stormdpzh
* POj: 1631 Bridging signals
* Created Time: 2012/5/18 18:40:46
*/
#include <iostream>
#include <cstdio>
#include <cstring>
#include <string>
#include <cmath>
#include <vector>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <algorithm>
#include <functional>
#define sz(v) ((int)(v).size())
#define rep(i, n) for(int i = 0; i < n; i++)
#define repf(i, a, b) for(int i = a; i <= b; i++)
#define repd(i, a, b) for(int i = a; i >= b; i--)
#define out(n) printf("%d\n", n)
#define wh(n) while(scanf("%d", &n) != EOF)
#define whz(n) while(scanf("%d", &n) != EOF && n != 0)
#define lint long long
using namespace std;
const int MaxN = 40005;
int n;
int data[MaxN];
int dp[MaxN];
int c[MaxN];
int siz;
void init()
{
rep(i, n) scanf("%d", &data[i + 1]);
memset(dp, 0, sizeof(dp));
memset(c, 0, sizeof(c));
dp[1] = 1;
c[1] = data[1];
siz = 1;
}
int bsearch(int i)
{
int l = 1;
int h = siz;
while(l <= h) {
int mid = (l + h) >> 1;
if(data[i] > c[mid]) l = mid + 1;
else if(data[i] < c[mid]) h = mid - 1;
}
return l;
}
int gao()
{
repf(i, 2, n) {
int j;
if(data[i] <= c[1]) j = 1;
else if(data[i] > c[siz]) j = ++siz;
else j = bsearch(i);
c[j] = data[i];
dp[i] = j;
}
return siz;
}
int main()
{
int t;
scanf("%d", &t);
while(t--) {
scanf("%d", &n);
init();
int res = gao();
out(res);
}
return 0;
}