题意我就不说了
 
解析: 莫队,先预处理出以i为右端点的区间的gcd值,有一些连续的区间的gcd值是相同的,比如[j,i],[j+1,i],[j+2,i]的gcd值是相同的,我们可以把[j,j+2]这个
区间保存下来。同时也预处理出以i为左端点的,最后用莫队算法。详见代码实现。
 
代码
#include<cstdio>
#include<vector>
#include<cstring>
#include<string>
#include<cmath>
#include<algorithm>
using namespace std;
const int maxn=;
typedef __int64 LL;
int N,M,A[maxn],block;
struct Ques
{
int x,y,id;
Ques(int x=,int y=,int id=):x(x),y(y),id(id){}
bool operator < (const Ques& t) const
{
int a=x/block,b=t.x/block; //排序
if(a!=b) return a<b;
return y<t.y;
}
}ques[maxn];
int gcd(int a,int b){ return b==?a:gcd(b,a%b); }
struct node
{
int id,g;
node(int id=,int g=):id(id),g(g){}
};
vector<node> vl[maxn],vr[maxn];
void GetLe()
{
for(int i=;i<=N;i++) //得到以i为右端点连续区间的gcd值
{
if(i==){ vl[i].push_back(node(i,A[i])); continue; }
int g=A[i],id=i;
int Size=vl[i-].size();
for(int j=;j<Size;j++)
{
node& t=vl[i-][j];
int ng=gcd(t.g,g);
if(ng!=g) vl[i].push_back(node(id,g));
g=ng; id=t.id;
}
vl[i].push_back(node(id,g));
}
}
void GetRi() //同理
{
for(int i=N;i>=;i--)
{
if(i==N){ vr[i].push_back(node(i,A[i])); continue; }
int g=A[i],id=i;
int Size=vr[i+].size();
for(int j=;j<Size;j++)
{
node& t=vr[i+][j];
int ng=gcd(t.g,g);
if(ng!=g) vr[i].push_back(node(id,g));
g=ng; id=t.id;
}
vr[i].push_back(node(id,g));
}
}
LL WorkLe(int x,int y)
{
int Size=vl[y].size();
int ny=y;
LL ret=;
for(int i=;i<Size;i++)
{
node& t=vl[y][i];
if(t.id>=x)
{
ret+=(LL)t.g*(ny-t.id+);
ny=t.id-; //跳过去
}
else{ ret+=(LL)t.g*(ny-x+); break; }
}
return ret;
}
LL WorkRi(int x,int y)
{
int nx=x;
LL ret=;
int Size=vr[x].size();
for(int i=;i<Size;i++)
{
node& t=vr[x][i];
if(t.id<=y)
{
ret+=(LL)t.g*(t.id-nx+);
nx=t.id+;
}
else { ret+=(LL)t.g*(y-nx+); break; }
}
return ret;
}
LL ans[maxn];
void solve()
{
for(int i=;i<=N;i++) vl[i].clear(),vr[i].clear();
block=(int)sqrt(N+0.5); //分块
sort(ques,ques+M); //排序
GetLe(); //得到左边连续相同的gcd区间
GetRi(); //得到右边连续相同的gcd区间
int x=,y=;
LL ret=;
for(int i=;i<M;i++) //莫队的主要实现部分
{
Ques& q=ques[i];
while(y<q.y){ y++; ret+=WorkLe(x,y); }
while(y>q.y){ ret-=WorkLe(x,y); y--; }
while(x<q.x){ ret-=WorkRi(x,y); x++; }
while(x>q.x){ x--; ret+=WorkRi(x,y); }
ans[q.id]=ret; //保存答案
}
for(int i=;i<M;i++) printf("%lld\n",ans[i]); //输出
}
int main()
{
int T;
scanf("%d",&T);
while(T--)
{
scanf("%d",&N);
for(int i=;i<=N;i++) scanf("%d",&A[i]);//输入
scanf("%d",&M);
int x,y;
for(int i=;i<M;i++)
{
scanf("%d%d",&x,&y);
ques[i]=Ques(x,y,i); //离线保存查询
}
solve();
}
return ;
}

Hdu5381-The sum of gcd(莫队)的更多相关文章

  1. hdu5381 The sum of gcd]莫队算法

    题意:http://acm.hdu.edu.cn/showproblem.php?pid=5381 思路:这个题属于没有修改的区间查询问题,可以用莫队算法来做.首先预处理出每个点以它为起点向左和向右连 ...

  2. hdu 5381 The sum of gcd 莫队+预处理

    The sum of gcd Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) P ...

  3. hdu 4676 Sum Of Gcd 莫队+phi反演

    Sum Of Gcd 题目连接: http://acm.hdu.edu.cn/showproblem.php?pid=4676 Description Given you a sequence of ...

  4. HDU-4676 Sum Of Gcd 莫队+欧拉函数

    题意:给定一个11~nn的全排列AA,若干个询问,每次询问给出一个区间[l,r][l,r],要求得出∑l≤i<j≤r  gcd(Ai,Aj)的值. 解法:这题似乎做的人不是很多,蒟蒻当然不会做只 ...

  5. hdu 4676 Sum Of Gcd 莫队+数论

    题目链接 给n个数, m个询问, 每个询问给出[l, r], 问你对于任意i, j.gcd(a[i], a[j]) L <= i < j <= R的和. 假设两个数的公约数有b1, ...

  6. HDOJ 5381 The sum of gcd 莫队算法

    大神题解: http://blog.csdn.net/u014800748/article/details/47680899 The sum of gcd Time Limit: 2000/1000 ...

  7. hdu5381 The sum of gcd

    莫队算法,预处理出每个数字往后的gcd情况,每个数字的gcd只可能是他的因子,因此后面最多只可能有logn种,可以先预处理出,然后套莫队算法,复杂度O(n*sqrt(n)*log(n)). 代码 #i ...

  8. [CSP-S模拟测试]:sum(数学+莫队)

    题目传送门(内部题63) 输入格式 第一行有一个整数$id$,表示测试点编号.第一行有一个整数$q$,表示询问组数.然后有$q$行,每行有两个整数$n_i,m_i$. 输出格式 一共有$q$行,每行一 ...

  9. HDU 4676 Sum Of Gcd 【莫队 + 欧拉】

    任意门:http://acm.hdu.edu.cn/showproblem.php?pid=4676 Sum Of Gcd Time Limit: 10000/5000 MS (Java/Others ...

随机推荐

  1. DL,DT,DD,比传统table更语义,解析更快的table列表方式

    使用dl,dt,dd替代传统的table布局 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" & ...

  2. Hive 6、Hive DML(Data Manipulation Language)

    DML主要是对Hive 表中的数据进行操作的(增 删 改),但是由于Hadoop的特性,所以单条的修改.删除,其性能会非常的低所以不支持进行级操作: 主要说明一下最常用的批量插入数据较为常用的方法: ...

  3. lucene 高亮显示

    原文地址: http://blog.csdn.net/javaman_chen/article/details/8224407 Lucene针对高亮显示功能提供了两种实现方式,分别是Highlight ...

  4. zoj 3706 Break Standard Weight(dp)

    Break Standard Weight Time Limit: 2 Seconds                                     Memory Limit: 65536 ...

  5. python3-day4(yield)

    1.yield 迭代器是访问集合元素的一种方式.迭代器对象从集合的第一个元素开始访问,直到所有的元素被访问完结束.迭代器只能往前不会后退,不过这也没什么,因为人们很少在迭代途中往后退.另外,迭代器的一 ...

  6. 【git 问题小说说】 git add时候报错:LF will be replaced by CRLF

    本文来自:http://blog.csdn.net/loovejava/article/details/22114477 最近工作在window平台,不怎么使用命令行了所以导致很多命令都不熟悉啦 哈哈 ...

  7. Android 打造形形色色的进度条 实现可以如此简单

    转载请标明出处:http://blog.csdn.net/lmj623565791/article/details/43371299 ,本文出自:[张鸿洋的博客] 1.概述 最近需要用进度条,秉着不重 ...

  8. nignx日志格式

    web-master的nginx格式: log_format web_format '$remote_addr $remote_port $remote_user [$time_local] ' '& ...

  9. <经验杂谈>C#/.Net字符串操作方法小结

    字符串操作是C#中最基本的.最常见的.也是用的最多的,以下我总结 了几种常见的方法 1.把字符串按照分隔符转换成 List /// <summary> /// 把字符串按照分隔符转换成 L ...

  10. Web Api 跨域解决方案

    一.跨域问题的由来 同源策略:出于安全考虑,浏览器会限制脚本中发起的跨站请求,浏览器要求JavaScript或Cookie只能访问同域下的内容. 正是由于这个原因,我们不同项目之间的调用就会被浏览器阻 ...