hdu5288 OO’s Sequence
Problem Description
OO has got a array A of size n ,defined a function f(l,r) represent the number of i (l<=i<=r) , that there's no j(l<=j<=r,j<>i) satisfy ai mod aj=0,now OO want to know
∑i=1n∑j=inf(i,j) mod (109+7).
Input
There are multiple test cases. Please process till EOF.
In each test case:
First line: an integer n(n<=10^5) indicating the size of array
Second line:contain n numbers ai(0<ai<=10000)
In each test case:
First line: an integer n(n<=10^5) indicating the size of array
Second line:contain n numbers ai(0<ai<=10000)
Output
For each tests: ouput a line contain a number ans.
Sample Input
5
1 2 3 4 5
Sample Output
23
题意:给你n个数,让你找出各个区间内不被任何a[j]整除的i的个数,并输出所有区间的个数和。
思路:因为算的是总的个数,所以我们可以算每一个数所贡献的个数。我们可以记录离它最近的左边的因数的下标l[i]和右边的因数的下标r[i],那么它贡献的个数是(r[i]-i)*(i-l[i]).找的时候可以先找l[i],即依次枚举它的因数,看之前有没有因数的下标,并且依次更新最大的,这里可以用mapx[i]记录前面已经判断过的数的最大下标,找r[i]的时候也是一样。
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<math.h>
#include<vector>
#include<set>
#include<queue>
#include<stack>
#include<string>
#include<algorithm>
using namespace std;
#define maxn 100060
#define ll long long
#define MOD 1000000007
//const int MOD=1e9+7;
int a[maxn],l[maxn],r[maxn];
int mapx[maxn];
int main()
{
int n,m,i,j;
int sum;
while(scanf("%d",&n)!=EOF)
{
for(i=1;i<=n;i++){
scanf("%d",&a[i]);
}
memset(mapx,0,sizeof(mapx));
for(i=1;i<=n;i++){
l[i]=0;
for(j=1;j*j<=a[i];j++){
if(a[i]%j==0){
if(mapx[j]){
l[i]=max(l[i],mapx[j]);
}
if(mapx[a[i]/j]){
l[i]=max(l[i],mapx[a[i]/j]);
}
}
}
mapx[a[i]]=i;
}
memset(mapx,0,sizeof(mapx));
for(i=n;i>=1;i--){
r[i]=n+1;
for(j=1;j*j<=a[i];j++){
if(a[i]%j==0){
if(mapx[j]){
r[i]=min(r[i],mapx[j]);
}
if(mapx[a[i]/j]){
r[i]=min(r[i],mapx[a[i]/j]);
}
}
}
mapx[a[i]]=i;
}
sum=0;
for(i=1;i<=n;i++){
sum=((ll)sum+(ll)(i-l[i])*(ll)(r[i]-i))%MOD;
}
printf("%d\n",sum);
}
return 0;
}