Cho một dãy gồm n số nguyên. Bạn được chọn một số phần tử, không nhất thiết nằm cạnh nhau, nhưng phải giữ nguyên thứ tự xuất hiện của chúng trong dãy ban đầu. Hãy tìm số phần tử lớn nhất có thể chọn sao cho mỗi giá trị được chọn sau đều lớn hơn nghiêm ngặt giá trị đứng trước nó.
Input
Dòng đầu chứa số nguyên n.
Dòng thứ hai chứa n số nguyên a1,a2,…,an.
Output
In một số nguyên: độ dài lớn nhất của một dãy con tăng nghiêm ngặt.
Constraints
1≤n≤2⋅105.
1≤ai≤109 với mọi 1≤i≤n.
Đáp án là một số nguyên trong đoạn từ 1 đến n.
Các vị trí được chọn phải tăng dần, còn các giá trị tương ứng phải tăng nghiêm ngặt; hai giá trị bằng nhau không thể đứng liên tiếp trong dãy được chọn.
Scoring
Subtask 1 (50% số điểm): n≤2000.
Subtask 2 (50% số điểm): Không có giới hạn bổ sung.
Example
Test 1
Input
8
5 1 4 2 3 9 6 7
Output
5
Giải thích: Có thể chọn 1,2,3,6,7, nên đáp án ít nhất là 5. Độ dài tốt nhất của dãy tăng kết thúc lần lượt tại tám vị trí là 1,1,2,2,3,4,4,5; vì giá trị lớn nhất là 5, không thể chọn được 6 phần tử.
Lời giải tóm tắt
Phân tích: Gọi dp[i] là độ dài dãy con tăng dài nhất kết thúc tại vị trí i. Công thức trực tiếp phải xét mọi vị trí trước đó nhỏ hơn a_i, dẫn tới O(n^2) và không đủ nhanh khi n = 200000.
Phân tích: Với mỗi độ dài k, chỉ cần giữ giá trị kết thúc nhỏ nhất có thể của một dãy tăng dài k. Một đuôi nhỏ hơn luôn thuận lợi ít nhất bằng một đuôi lớn hơn đối với mọi phần tử tương lai.
Thuật toán: Duy trì mảng tail, trong đó tail[k-1] là đuôi nhỏ nhất đã biết của một dãy tăng dài k. Với mỗi giá trị x, tìm bằng lower_bound vị trí đầu tiên có giá trị không nhỏ hơn x. Nếu không có vị trí ấy, nối x vào cuối; ngược lại, thay đuôi tại vị trí tìm được bằng x.
Thuật toán: Dùng lower_bound, không dùng upper_bound, vì dãy phải tăng nghiêm ngặt và các giá trị bằng nhau không được làm tăng độ dài.
Chứng minh tính đúng đắn: Sau mỗi tiền tố, tail[k-1] là đuôi nhỏ nhất của mọi dãy tăng dài k trong tiền tố đó. Khi xử lý x, vị trí do lower_bound tìm được chính là độ dài lớn nhất có thể nối thêm x; việc thay bằng x tạo một đại diện không tệ hơn đại diện cũ và không làm mất độ dài nào đã đạt được. Nếu x lớn hơn mọi đuôi, ta tạo được một dãy dài hơn đúng một phần tử. Bởi quy nạp, số phần tử của tail sau cùng bằng độ dài dãy con tăng dài nhất.