hdu 6155 - Subsequence Count 線段樹+dp+矩陣

參考的原博客:http://www.cnblogs.com/iRedBean/p/7398272.html
這裏寫圖片描述

#include <bits/stdc++.h>
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
using namespace std;
int n,q;
const int maxn=1e5+9;
const long long mod=1e9+7;

struct matrix
{
    long long m[3][3];
};
const matrix mp[2]= {{1,0,0,1,1,0,1,0,1},{1,1,0,0,1,0,0,1,1}};
matrix data[maxn<<2];
int f[maxn<<2];
char s[maxn];

matrix mul(matrix a,matrix b)
{
    matrix tmp;
    for(int i=0; i<3; i++)
    {
        for(int j=0; j<3; j++)
        {
            tmp.m[i][j]=0;
            for(int k=0; k<3; k++)
                tmp.m[i][j]+=(a.m[i][k]*b.m[k][j])%mod;
            tmp.m[i][j]%=mod;
        }
    }
    return tmp;
}
void flip(matrix &x)
{
    swap(x.m[0][0], x.m[0][1]);
    swap(x.m[1][0], x.m[1][1]);
    swap(x.m[2][0], x.m[2][1]);
    swap(x.m[0][0], x.m[1][0]);
    swap(x.m[0][1], x.m[1][1]);
}
void pushup(int rt)
{
    data[rt]= mul(data[rt<<1],data[rt<<1|1]);
}
void pushdown(int rt)
{
    if(f[rt])
    {
        flip(data[rt<<1]);
        flip(data[rt<<1|1]);
        f[rt<<1]^=f[rt];
        f[rt<<1|1]^=f[rt];
        f[rt]=0;
    }
}
void build(int l,int r,int rt)
{
    f[rt]=0;
    if(l==r)
    {
        int t=s[l]-'0';
        data[rt]=mp[t];
        return;
    }
    int m=r+l>>1;
    build(lson);
    build(rson);
    pushup(rt);
}
void update(int L,int R,int l,int r,int rt)
{
    if(L<=l&&r<=R)
    {
        f[rt]=1-f[rt];
        flip(data[rt]);
        return;
    }
    int m=l+r>>1;
    pushdown(rt);
    if(L<=m) update(L,R,lson);
    if(m<R) update(L,R,rson);
    pushup(rt);
}
matrix query(int L,int R,int l,int r,int rt)
{
    if(L==l&&r==R)
        return data[rt];
    int m=l+r>>1;
    pushdown(rt);
    if(R<=m) return query(L,R,lson);
    else if(L>m) return query(L,R,rson);
    else return mul(query(L,m,lson),query(m+1,R,rson));
}
int main()
{
    int t;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d%d",&n,&q);
        scanf("%s",s+1);
        build(1,n,1);
        while(q--)
        {
            int op,l,r;
            scanf("%d%d%d",&op,&l,&r);
            if(op==1)
                update(l,r,1,n,1);
            else
            {
                matrix x=query(l,r,1,n,1);
                printf("%I64d\n",(x.m[2][0]+x.m[2][1])%mod);
            }
        }
    }
    return 0;
}
發佈了174 篇原創文章 · 獲贊 64 · 訪問量 6萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章