See LCS again
Time Limit: 1000 MS | memory limit: 65535 KB
Difficulty: 3
Description
There are a, B two sequences, the number of elements in the sequence is n, m;
Each element in the sequence are different and less than 100000.
Calculate the length of the longest common subsequence of A and B.
Input
The input has multicases. Each test case consists of three lines;
The first line consist two integers n, m (1 <= n, m <= 100000 );
The second line with N integers, expressed sequence;
The third line with M integers, expressed sequence B;
Output
For each set of test cases, output the length of the longest common subsequence of A and B, in a single line.
Sample Input
5 4
1 2 6 5 4
1 3 5 4
Sample output
3
Uploaded
TC _ Hu rendong
Solution: An nlogn Algorithm for converting LCS to LCS. Is a strictly rising LCS.
The first is LCS. We save the positions where each element in sequence A appears in sequence B, sort them in descending order, and then place them into each corresponding element of sequence, then it is converted to the longest ascending subsequence of the new sequence. For example: A [] = {A, B, C,} B [] = {A, B, C, B, A, D}, then a, B, the positions where C appears in B are {0, 4}, {1, 3}, {2 }. Each descendant is sorted in descending order into the sequence {4, 0, 2, 3, 1} in descending order, so that each element can be obtained only once.
The following problem is that the sub-sequence in ascending order is required, that is, Lis.
In special circumstances, it may degrade very seriously.
1 #include <iostream> 2 #include <cstdio> 3 #include <cstring> 4 #include <cmath> 5 #include <algorithm> 6 #include <climits> 7 #include <vector> 8 #include <queue> 9 #include <cstdlib>10 #include <string>11 #include <set>12 #include <stack>13 #define LL long long14 #define pii pair<int,int>15 #define INF 0x3f3f3f3f16 using namespace std;17 struct info{18 int num,pos;19 };20 int n,m,tot,sa[100010],sc[200010],q[200010],head,tail;21 info sb[100010];22 bool cmp(const info &x,const info &y){23 return x.num < y.num;24 }25 int bsearch(int lt,int rt,int val){26 int mid,pos = -1;27 while(lt <= rt){28 int mid = (lt+rt)>>1;29 if(val <= sb[mid].num){30 pos = mid;31 rt = mid-1;32 }else lt = mid+1;33 }34 return pos;35 }36 int binsearch(int lt,int rt,int val){37 while(lt <= rt){38 int mid = (lt+rt)>>1;39 if(q[mid] < val) lt = mid+1;40 else rt = mid-1;41 }42 return lt;43 }44 int main() {45 while(~scanf("%d %d",&n,&m)){46 head = tail = tot = 0;47 for(int i = 1; i <= n; i++) scanf("%d",sa+i);48 for(int i = 1; i <= m; i++){49 scanf("%d",&sb[i].num);50 sb[i].pos = i;51 }52 sort(sb+1,sb+m+1,cmp);53 for(int i = 1; i <= n; i++){54 int tmp = bsearch(1,m,sa[i]);55 while(tmp > 0 && sb[tmp].num == sa[i]) sc[tot++] = sb[tmp++].pos;56 }57 for(int i = 0; i < tot; i++){58 if(head == tail || q[head-1] < sc[i]){59 q[head++] = sc[i];60 }else{61 int tmp = binsearch(tail,head-1,sc[i]);62 q[tmp] = sc[i];63 }64 }65 printf("%d\n",head-tail);66 }67 return 0;68 }View code
Nyist 760 see LCS again