我以为稍微水一下O(n2)还是可以过的,毕竟只有3个test case。死活不让啊。
1 #include <bits/stdc++.h> 2 #define MAX(X,Y) ((X) > (Y) ? (X) : (Y)) 3 #define MIN(X,Y) ((X) < (Y) ? (X) : (Y)) 4 #define pii pair<int,int> 5 #define INF 0x7f7f7f7f 6 #define LL long long 7 using namespace std; 8 const int N=10005; 9 struct node 10 { 11 int L, R, ans; 12 }que[N]; 13 struct node1 14 { 15 int ll, rr, gcd; 16 node1(){}; 17 node1(int ll,int rr,int gcd):ll(ll),rr(rr),gcd(gcd){}; 18 }reg[N][50]; 19 20 int _gcd(int a, int b){return b == 0 ? a : _gcd(b, a % b);} 21 22 int seq[N], n, q, pre[N]; 23 int cnt[N]; 24 void pre_cal() 25 { 26 memset(cnt,0,sizeof(cnt)); 27 reg[n][0]=node1(n,n,seq[n]); //最后一个特殊处理 28 cnt[n]++; 29 for(int i=n-1; i>=1; i--) 30 { 31 int R=i, gcd=seq[i], tmp; 32 for(int j=0; j<cnt[i+1]; j++) 33 { 34 node1 &t=reg[i+1][j]; 35 tmp=_gcd(gcd, t.gcd ); 36 if(tmp!=gcd) reg[i][cnt[i]++]=node1(i, R, gcd); 37 gcd=tmp; 38 R=t.rr; 39 } 40 reg[i][cnt[i]++]=node1(i, R, gcd); 41 } 42 } 43 44 void cal() 45 { 46 for(int i=1; i<=n; i++) 47 { 48 pre[i-1]=0; 49 pre[i]=seq[i]; 50 int p=0; 51 for(int j=i+1; j<=n; j++) 52 { 53 if(j>reg[i][p].rr) p++; 54 pre[j]=reg[i][p].gcd; 55 pre[j]+=pre[j-1]; 56 } 57 for(int j=1; j<=q; j++) 58 if( i>=que[j].L && i<=que[j].R ) 59 que[j].ans+=pre[que[j].R]-pre[i-1]; 60 } 61 for(int i=1; i<=q; i++) printf("%d\n",que[i].ans); 62 } 63 int main() 64 { 65 //freopen("input.txt", "r", stdin); 66 int t, L, R; 67 cin>>t; 68 while(t--) 69 { 70 scanf("%d", &n); 71 for(int i=1; i<=n; i++) scanf("%d", &seq[i]); 72 73 scanf("%d", &q); 74 for(int i=1; i<=q; i++) 75 { 76 scanf("%d %d", &que[i].L, &que[i].R); 77 que[i].ans=0; 78 } 79 pre_cal(); 80 cal(); 81 } 82 83 return 0; 84 }
TLE代码
时间: 2024-10-09 21:26:24