WUST OJ 1593: Count Zeros(线段树)

来源:互联网 发布:合泰触摸单片机芯片 编辑:程序博客网 时间:2024/06/03 17:02

1593: Count Zeros

Time Limit: 1 Sec  Memory Limit: 128 MB  64bit IO Format: %lld
Submitted: 113  Accepted: 17
[Submit][Status][Web Board]

Description

Blue Wang is addicted in Math. He calculates all kinds of math problems all day. The answer may be very large, but he writes it on the paper by hand.
Sometimes it’s boring because he must write many zeros at the tail of the answer sequence.
So he wants to know how many zeros at the tail of answer when he calculates the product of a continuous integer sequence.
 

Input

There are multiple test cases. For each test case: the first line contains two integers n,m(n,m<100000) denoting the number of integers and queries. The second line are n integers A1,A2,A3...An(Ai<=100,1<=i<=n) .The next m lines, each line contains three numbers  op,x,y ,If op=0, you need help him calculate the answer (zeros at the tail of answer When he calculates the product of a continuous integer sequence between x,y) and output it. If op=1, you need change the integer at the position of x to y.All integers are not smaller than 0.
 

Output

For each query, if op=0 , output a integer which denotes the number of zeros Blue Wang needs write at the tail of answer. 

Sample Input 

5 3

1 2 3 4 10

0 1 5

1 4 5

0 1 5

Sample Output

1

2

Source

武汉科技大学第二届移动互联网应用设计大赛(A类)暨华中地区程序设计竞赛专业组

思路:线段树区间查询和单点更新。节点储存元素因子2的个数和因子5的个数,以及标记该区间是否有为0的元素。

#include<cstdio>#include<algorithm>#include<cstring>using namespace std;const int MAX=1e6;struct lenka{    int tag;    int l,r;    int num2,num5;}A[MAX];int a[MAX],QWQ,num2,num5;void build(int k,int l,int r){    A[k].l=l,A[k].r=r;    A[k].num2=A[k].num5=0;    if(l==r)    {        if(a[l]==0)A[k].tag=1;        else        {            A[k].tag=0;            while(a[l]%2==0)A[k].num2++,a[l]/=2;            while(a[l]%5==0)A[k].num5++,a[l]/=5;        }        return;    }    build(2*k,l,(l+r)/2);    build(2*k+1,(l+r)/2+1,r);    A[k].num2=A[2*k].num2+A[2*k+1].num2;    A[k].num5=A[2*k].num5+A[2*k+1].num5;    A[k].tag=A[2*k].tag|A[2*k+1].tag;}void change(int k,int x,int y){    if(x==A[k].l&&x==A[k].r)    {        A[k].num2=A[k].num5=0;        if(y==0)A[k].tag=1;        else        {            A[k].tag=0;            a[x]=y;            while(a[x]%2==0)A[k].num2++,a[x]/=2;            while(a[x]%5==0)A[k].num5++,a[x]/=5;        }        return;    }    if(x<=A[2*k].r)change(2*k,x,y);    else change(2*k+1,x,y);    A[k].num2=A[2*k].num2+A[2*k+1].num2;    A[k].num5=A[2*k].num5+A[2*k+1].num5;    A[k].tag=A[2*k].tag|A[2*k+1].tag;}void ask(int k,int l,int r){    if(l==A[k].l&&r==A[k].r)    {        if(A[k].tag)QWQ=1;        else        {            num2+=A[k].num2;            num5+=A[k].num5;        }        return;    }    if(r<=A[2*k].r)ask(2*k,l,r);    else if(l>=A[2*k+1].l)ask(2*k+1,l,r);    else    {        ask(2*k,l,A[2*k].r);        ask(2*k+1,A[2*k+1].l,r);    }}int main(){    int n,m;    while(scanf("%d%d",&n,&m)!=EOF)    {        for(int i=1;i<=n;i++)scanf("%d",&a[i]);        build(1,1,n);        while(m--)        {            int op,x,y;            scanf("%d%d%d",&op,&x,&y);            if(op==0)            {                QWQ=0;                num2=0;                num5=0;                ask(1,x,y);                if(QWQ)puts("1");                else printf("%d\n",min(num2,num5));            }            else change(1,x,y);        }    }    return 0;}



原创粉丝点击