AHOI2009 維護序列 線段樹

2022-05-03 19:39:10 字數 3301 閱讀 9928

老師交給小可可乙個維護數列的任務,現在小可可希望你來幫他完成。 有長為n的數列,不妨設為a1,a2,…,an 。有如下三種操作形式: (1)把數列中的一段數全部乘乙個值; (2)把數列中的一段數全部加乙個值; (3)詢問數列中的一段數的和,由於答案可能很大,你只需輸出這個數模p的值。

線段樹,打個乘法lazy標記即可

#include

const

int maxn = 100000 + 10;

struct

seg tree[maxn*4];

long

long p;

long

long n,m;

inline

void

pushup

(long

long root)

inline

void

buildtree

(long

long l,long

long r,long

long root)

long

long mid = l+r>>1;

buildtree(l,mid,root<<1);

buildtree(mid+1,r,root<<1|1);

pushup(root);

}inline

void

pushdown

(long

long root)

if (tree[root].add != 0)

}inline

void

updateadd

(long

long ql,long

long qr,long

long l,long

long r,long

long root,long

long x)

pushdown(root);

long

long mid = l+r>>1;

updateadd(ql,qr,l,mid,root<<1,x);

updateadd(ql,qr,mid+1,r,root<<1|1,x);

pushup(root);

}inline

void

updatemul

(long

long ql,long

long qr,long

long l,long

long r,long

long root,long

long x)

pushdown(root);

long

long mid = l+r>>1;

updatemul(ql,qr,l,mid,root<<1,x);

updatemul(ql,qr,mid+1,r,root<<1|1,x);

pushup(root);

}inline

long

long

query

(long

long ql,long

long qr,long

long l,long

long r,long

long root)

intmain

() else

if (op == 2) else

printf("%lld\n",query(l,r,1,n,1));

}return

0;}

#include

const

int maxn = 100000 + 10;

struct

seg tree[maxn*4];

long

long p;

long

long n,m;

inline

void

pushup

(long

long root)

inline

void

buildtree

(long

long l,long

long r,long

long root)

long

long mid = l+r>>1;

buildtree(l,mid,root<<1);

buildtree(mid+1,r,root<<1|1);

pushup(root);

}inline

void

pushdown

(long

long root)

if (tree[root].add != 0)

}inline

void

updateadd

(long

long ql,long

long qr,long

long l,long

long r,long

long root,long

long x)

pushdown(root);

long

long mid = l+r>>1;

updateadd(ql,qr,l,mid,root<<1,x);

updateadd(ql,qr,mid+1,r,root<<1|1,x);

pushup(root);

}inline

void

updatemul

(long

long ql,long

long qr,long

long l,long

long r,long

long root,long

long x)

pushdown(root);

long

long mid = l+r>>1;

updatemul(ql,qr,l,mid,root<<1,x);

updatemul(ql,qr,mid+1,r,root<<1|1,x);

pushup(root);

}inline

long

long

query

(long

long ql,long

long qr,long

long l,long

long r,long

long root)

intmain

() else

if (op == 2) else

printf("%lld\n",query(l,r,1,n,1));

}return

0;}

線段樹 AHOI 2009 維護序列

老師交給小可可乙個維護數列的任務,現在小可可希望你來幫他完成。有長為n的數列,不妨設為a1,a2,an 有如下三種操作形式 1 把數列中的一段數全部乘乙個值 2 把數列中的一段數全部加乙個值 3 詢問數列中的一段數的和,由於答案可能很大,你只需輸出這個數模p的值。第一行兩個整數n和p 1 p 100...

AHOI2009 維護序列

題目描述 有乙個長為 n n leq 10 5 的序列,支援三種操作,分別是給一段區間 l,r 內的所有數加上 乘上乙個數,以及求一段區間 l,r 中的數字的和。輸入樣例 7 43 1 2 3 4 5 6 7 51 2 5 5 3 2 4 2 3 7 9 3 1 3 3 4 7 輸出樣例 2 358...

bzoj1798 ahoi2009 維護序列

time limit 30 sec memory limit 64 mb submit 3714 solved 1364 submit status discuss 老師交給小可可乙個維護數列的任務,現在小可可希望你來幫他完成。有長為n的數列,不妨設為a1,a2,an 有如下三種操作形式 1 把數列...