#include <bits/stdc++.h>
using namespace std;
ifstream f("scmax.in");
ofstream g("scmax.out");
const int NMAX = 1e5 + 10;
int n,arb[4 * NMAX],value,dp[NMAX];
pair <int, int> v[NMAX];
bool cmp(pair <int, int> X, pair <int, int> Y){
return X.first < Y.first;
}
void update(int node, int lo, int hi, int x, int y){
if(lo == hi){
arb[node] = y;
return;
}
int mid = (lo + hi) / 2;
if(x <= mid)
update(2 * node, lo, mid, x, y);
if(x > mid)
update(2 * node + 1, mid + 1, hi, x, y);
arb[node] = max(arb[2 * node], arb[2 * node + 1]);
}
void query(int node, int lo, int hi, int x, int y){
if(lo > hi) return;
if(hi < x || lo > y) return;
if(lo >= x && hi <= y){
value = max(value, arb[node]);
return;
}
int mid = (lo + hi) / 2;
if(x <= mid)
query(2 * node, lo, mid, x, y);
if(y > mid)
query(2 * node + 1, mid + 1, hi, x, y);
}
int main(){
int i;
f >> n;
for(i = 1 ; i <= n ; i++){
f >> v[i].first;
v[i].second = i;
}
sort(v + 1, v + n + 1, cmp);
for(i = 1 ; i <= 4 * n ; i++)
arb[i] = 1;
for(i = 1 ; i <= n ; i++){
value = 0;
//g << v[i].first << " " << v[i].second << "\n";
query(1,1,n, 1, v[i].second - 1);
//g << value << "\n";
update(1,1,n,v[i].second, value + 1);
dp[v[i].second] = value + 1;
while(v[i].first == v[i + 1].first){
i++;
dp[v[i].second] = value + 1;
update(1,1,n,v[i].second, value + 1);
}
}
g << arb[1] << "\n";
return 0;
}