题意:P 工厂是一个生产纸箱的工厂。纸箱生产线在人工输入三个参数 n p a , , 之后,
即可自动化生产三边边长为
(a mod P,a^2 mod p,a^3 mod P)
(a^4 mod p,a^5 mod p,a^6 mod P)
....
(a^(3n-2) mod p,a^(3n-1) mod p,a^(3n) mod p)
的n个纸箱。在运输这些纸箱时,为了节约空间,必须将它们嵌套堆叠起来。
一个纸箱可以嵌套堆叠进另一个纸箱当且仅当它的最短边、次短边和最长边
长度分别严格小于另一个纸箱的最短边、次短边和最长边长度。这里不考虑
任何旋转后在对角线方向的嵌套堆叠。
你的任务是找出这n个纸箱中数量最多的一个子集,使得它们两两之间都可
嵌套堆叠起来。
2<=P<=2000000000,1<=a<=p-1,a^k mod p<>0,ap<=2000000000,1<=N<=50000
思路:先把n个纸箱求出来
按一维排序 另两维用二维树状数组
1 #include<iostream> 2 #include<cstdio> 3 #include<cstring> 4 #include<map> 5 #include<cmath> 6 #include<algorithm> 7 using namespace std; 8 #define MAXN 50000+100 9 struct number 10 { 11 long long x,y,z; 12 }; 13 int n,ans=0; 14 long long t,p; 15 long long b[MAXN]; 16 number a[MAXN]; 17 map<pair<int,int>,int> tree; 18 map<long long,int> home; 19 void my_sort(int i) 20 { 21 if(a[i].x>a[i].y) swap(a[i].x,a[i].y); 22 if(a[i].y>a[i].z) swap(a[i].z,a[i].y); 23 if(a[i].x>a[i].y) swap(a[i].x,a[i].y); 24 } 25 bool cmp(const number &A,const number &B) 26 { 27 if(A.x<B.x) return 1; 28 if(A.x>B.x) return 0; 29 if(A.y>B.y) return 1; 30 return 0; 31 } 32 33 void make_a() 34 { 35 int i; 36 long long temp=1; 37 for(i=1;i<=3*n;i++) 38 { 39 temp=temp*t%p; 40 if(i%3==1) a[i/3+1].x=temp; 41 else if(i%3==2) a[i/3+1].y=temp; 42 else 43 { 44 a[i/3].z=temp; 45 my_sort(i/3); 46 } 47 } 48 sort(a+1,a+n+1,cmp); 49 } 50 void discretization() 51 { 52 b[0]=-1; 53 int i,j=0; 54 for(i=1;i<=n;i++) 55 b[i]=a[i].y; 56 sort(b,b+n+1); 57 for(i=1;i<=n;i++) 58 { 59 if(b[i]!=b[i-1]) 60 home[b[i]]=++j; 61 else 62 home[b[i]]=j; 63 } 64 for(i=1;i<=n;i++) a[i].y=home[a[i].y]; 65 66 for(i=1;i<=n;i++) 67 b[i]=a[i].z; 68 sort(b,b+n+1); 69 j=0; 70 for(i=1;i<=n;i++) 71 { 72 if(b[i]!=b[i-1]) 73 home[b[i]]=++j; 74 else 75 home[b[i]]=j; 76 } 77 for(i=1;i<=n;i++) 78 a[i].z=home[a[i].z]; 79 } 80 int lowbit(int x) 81 { 82 return x&(x^(x-1)); 83 } 84 void update(int x,int y,int add) 85 { 86 for(int i=x;i<=n;i+=lowbit(i)) 87 for(int j=y;j<=n;j+=lowbit(j)) 88 tree[make_pair(i,j)]=max(tree[make_pair(i,j)],add); 89 } 90 int find(int x,int y) 91 { 92 int ans=0; 93 for(int i=x;i>0;i-=lowbit(i)) 94 for(int j=y;j>0;j-=lowbit(j)) 95 ans=max(ans,tree[make_pair(i,j)]); 96 return ans; 97 } 98 99 int main() 100 { 101 int temp; 102 scanf("%lld%lld%d",&t,&p,&n); 103 make_a(); 104 discretization(); 105 for(int i=1;i<=n;i++) 106 { 107 temp=find(a[i].y-1,a[i].z-1); 108 update(a[i].y,a[i].z,temp+1); 109 if(temp+1>ans) ans=temp+1; 110 } 111 printf("%d\n",ans); 112 return 0; 113 }