分析:(别人写的)

对于所有(l, r)区间,固定右区间,所有(li, r)一共最多只会有log个不同的gcd值,

可以nlogn预处理出所有不同的gcd区间,这样区间是nlogn个,然后对于询问离线处理,

用类似询问区间不同数字的方法,记录每个不同gcd最后出现的位置,然后用树状数组进行维护

注:我是看了这段文字会的,但是他的nlogn预处理我不会,我会nlog^2n的

dp[i][j]代表以i为右端点,向左延伸2^j个点(包括i)的gcd,然后因为这样的gcd满足递减,所以可以二分找区间

代码:

/*RunID: 678021
UserID: 96655
Submit time: 2016-04-19 23:44:20
Language: C++
Length: 2378 Bytes.
Result: Accepted
*/ #include <stdio.h>
#include <iostream>
#include <algorithm>
#include <string.h>
using namespace std;
typedef long long LL;
const int INF=0x3f3f3f3f;
const int N=1e4+;
int T,n,m,dp[N][];
struct ask{
int l,r,id;
bool operator<(const ask &rhs)const{
return r<rhs.r;
}
}p[N*];
struct Seg{
int l,r,v;
bool operator<(const Seg &rhs)const{
return r<rhs.r;
}
}seg[*N];
int erfen(int pos,int v){
int l=,r=pos;
while(l<r){
int mid=(l+r)>>;
int len=pos-mid+;
int now=pos,cur=-;
for(int i=;i>=;--i){
if(len&(<<i)){
if(cur==-)cur=dp[now][i];
else cur=__gcd(cur,dp[now][i]);
now-=(<<i);
}
}
if(cur<v)l=mid+;
else r=mid;
}
return (l+r)>>;
}
int hash[*N],tot,mat[*N];
int res[N*];
int c[N];
void add(int x,int t){
for(int i=x;i<=n;i+=i&(-i))
c[i]+=t;
}
int get(int x){
int ans=;
if(x==)return ;
for(int i=x;i>;i-=i&(-i))
ans+=c[i];
return ans;
}
int main(){
scanf("%d",&T);
while(T--){
scanf("%d%d",&n,&m);
for(int i=;i<=n;++i)
scanf("%d",&dp[i][]);
for(int i=;i<=m;++i)
scanf("%d%d",&p[i].l,&p[i].r),p[i].id=i;
for(int k=;(<<k)<=n;++k)
for(int i=n;i>;--i){
int j=i-(<<k)+;
if(j<)break;
j=i-(<<(k-));
dp[i][k]=__gcd(dp[i][k-],dp[j][k-]);
}
int cnt=;tot=;
for(int i=;i<=n;++i){
int last=-;
for(int j=i;j>;--j){
int tmp=dp[j][];
if(last!=-)tmp=__gcd(tmp,last);
last=tmp;
++cnt;
seg[cnt].l=j,seg[cnt].r=i,seg[cnt].v=last;
hash[++tot]=last;
j=erfen(i,last);
}
}
sort(hash+,hash++tot);
tot=unique(hash+,hash++tot)-hash-;
sort(p+,p++m);
sort(seg+,seg++cnt);
memset(mat,,sizeof(mat));
memset(c,,sizeof(c));
int now=;
for(int i=;i<=m;++i){
for(;now<=cnt&&seg[now].r<=p[i].r;++now){
int pos=lower_bound(hash+,hash++tot,seg[now].v)-hash;
if(seg[now].l>mat[pos]){
if(mat[pos])add(mat[pos],-);
add(seg[now].l,);
mat[pos]=seg[now].l;
}
}
res[p[i].id]=get(p[i].r)-get(p[i].l-);
}
for(int i=;i<=m;++i)
printf("%d\n",res[i]);
}
return ;
}

FZU2224 An exciting GCD problem 区间gcd预处理+树状数组的更多相关文章

  1. 区间gcd问题 HDU 5869 离线+树状数组

    题目大意:长度n的序列, m个询问区间[L, R], 问区间内的所有子段的不同GCD值有多少种. 子段就是表示是要连续的a[] 思路:固定右端点,预处理出所有的gcd,每次都和i-1的gcd比较,然后 ...

  2. ACM学习历程—51NOD 1685 第K大区间2(二分 && 树状数组 && 中位数)

    http://www.51nod.com/contest/problem.html#!problemId=1685 这是这次BSG白山极客挑战赛的E题. 这题可以二分答案t. 关键在于,对于一个t,如 ...

  3. [BZOJ2225][SPOJ2371]LIS2 - Another Longest Increasing Subsequence Problem:CDQ分治+树状数组+DP

    分析 这回试了一下三级标题,不知道效果怎么样? 回到正题,二维最长上升子序列......嗯,我会树套树. 考虑\(CDQ\)分治,算法流程: 先递归进入左子区间. 将左,右子区间按\(x\)排序. 归 ...

  4. HDU 5869 Different GCD Subarray Query (GCD种类预处理+树状数组维护)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5869 问你l~r之间的连续序列的gcd种类. 首先固定右端点,预处理gcd不同尽量靠右的位置(此时gc ...

  5. 【HDU4947】GCD Array(莫比乌斯反演+树状数组)

    点此看题面 大致题意: 一个长度为\(n\)的数组,实现两种操作:将满足\(gcd(i,k)=d\)的\(a_i\)加上\(v\),询问\(\sum_{i=1}^xa_i\). 对于修改操作的推式子 ...

  6. A Simple Problem with Integers 多树状数组分割,区间修改,单点求职。 hdu 4267

    A Simple Problem with Integers Time Limit: 5000/1500 MS (Java/Others)    Memory Limit: 32768/32768 K ...

  7. poj_3468: A Simple Problem with Integers (树状数组区间更新)

    题目是对一个数组,支持两种操作 操作C:对下标从a到b的每个元素,值增加c: 操作Q:对求下标从a到b的元素值之和. 这道题也可以用线段树解,本文不做描述,下面分析如何用树状数组来解决这道题. 先把问 ...

  8. POJ 3468 A Simple Problem with Integers(树状数组区间更新)

    A Simple Problem with Integers Time Limit: 5000MS   Memory Limit: 131072K Total Submissions: 97217   ...

  9. poj 3468: A Simple Problem with Integers (树状数组区间更新)

    题目链接: http://poj.org/problem?id=3468 题目是对一个数组,支持两种操作 操作C:对下标从a到b的每个元素,值增加c: 操作Q:对求下标从a到b的元素值之和. 这道题也 ...

随机推荐

  1. 只允许输入数字的TextBox控件

    [实例说明] 可以在TextBox控件中轻松地输入文本信息,输入的文本信息可以包括字母.数字.汉字等. 如果需要用户在TextBox控件中填写年龄信息,那么年龄信息应当只允许数字,怎么限制用户输入其他 ...

  2. HTML5的简介

    前言:作为IOS开发工程师,终会接触到网页前端开发,甚至可能会有 用HTML5开发IOS的app客户端的需求.比如现在上架的app就有比如理财类型的app有的就用HTML开发的,从理财类型的app需求 ...

  3. hggroup和adress

    hggroup通常放在标签内部,不过不做强制要求! ​adress 通常用于作者的联系信息.比如名字,Email,电话,地址.标签内字体显示斜体. ​ 与 标签的比较:比div简洁,更少的用到id或c ...

  4. 当在Win8下安装msi类型的文件出现errorcode 2503的解决方法

    Win8安装程序出现2502.2503错误解决方法 在Win8中,在安装msi安装包的时候常常会出现代码为2502.2503的错误.其实这种错误是由于安装权限不足造成的,可以这种msi的安装包不像其他 ...

  5. MySQL基础学习之索引

    创建新表新索引 CREATE TABLE 表名(数据名 类型,INDEX  索引名称(属性)) 创建存在表的索引 CREATE INDEX 索引名称  ON 表名(属性) 修改索引 ALTER TAB ...

  6. jquery div拖动效果示例代码

    div拖动效果想必大家都有见到过吧,实现的方法也是有很多的,下面为大家将介绍使用jquery是如何实现的,感兴趣的朋友不要错过 复制代码代码如下: <%@ page language=" ...

  7. Django数据操作

    1.一个模型类代表数据库中的一个表,一个模型类的实例代表这个数据库表中的一条特定的记录. 2.管理器和查询集. 查询集QuerySet表示从数据库中取出来的对象的集合.它可以含有零个.一个或者多个过滤 ...

  8. C#常用正则过滤

    //string regexstr = @"<[^>]*>"; //去除所有的标签 //@"<script[^>]*?>.*?< ...

  9. 一步步学习NHibernate(4)——多对一,一对多,懒加载(1)

    请注明转载地址:http://www.cnblogs.com/arhat 通过上一章的学习,我们学会如何使用NHibernate对数据的简单查询,删除,更新和插入,那么如果说仅仅是这样的话,那么NHi ...

  10. ASP.NET MVC Spring.NET NHibernate 整合

    请注明转载地址:http://www.cnblogs.com/arhat 在整合这三个技术之前,首先得说明一下整合的步骤,俗话说汗要一口一口吃,事要一件一件做.同理这个三个技术也是.那么在整合之前,需 ...