HDU - 5475 An easy problem(线段树)
生活随笔
收集整理的這篇文章主要介紹了
HDU - 5475 An easy problem(线段树)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
題目鏈接:點擊查看
題目大意:給定n次操作和一個m,每次操作后對m取模,每次操作分為兩種,初始化當前的數為1:
題目分析:對于這個題,第一反應是模擬,果不其然的WA了,后來反思為什么會WA,原因應該是除法對于取模不能分開計算,也就是說雖然乘法可以分布取模,但是除法卻不可以,所以根本沒有辦法模擬,那么我們換個思路,這個題目也是很巧,他每次除的數總是之前已經乘過的,那么我們不就可以轉化為不乘之前的那個數然后求積,這樣就能正常取模運算了。
這個思路確實很巧,可是不是我自己想出來的。。就是先將線段樹初始化為1,每次操作維護一下線段樹,若是操作1,就將當前位置的數改為x,若是操作2,就將x位置的數改為1,然后每次用query函數求出區間和,區間正是從1到當前位置。具體詳見代碼:
#include<iostream> #include<cstdio> #include<string> #include<cstring> #include<algorithm> #include<stack> #include<queue> #include<map> #include<sstream> #include<cmath> using namespace std;typedef long long LL;const int inf=0x3f3f3f3f;const int N=1e5+100;int mod;struct Node {int l,r;LL sum; }tree[N<<2];void build(int k,int l,int r) {tree[k].l=l;tree[k].r=r;tree[k].sum=1;if(l==r){return;}int mid=(l+r)>>1;build(k<<1,l,mid);build(k<<1|1,mid+1,r); }void update(int k,int pos,int val) {if(tree[k].l==tree[k].r){tree[k].sum=val;return;}int mid=(tree[k].l+tree[k].r)>>1;if(mid>=pos)update(k<<1,pos,val);elseupdate(k<<1|1,pos,val);tree[k].sum=tree[k<<1].sum*tree[k<<1|1].sum%mod; }LL query(int k,int l,int r) {if(tree[k].l>r||tree[k].r<l)return 1;//注意這里,因為是乘法,所以不符合條件的返回1而不是0if(tree[k].l>=l&&tree[k].r<=r)return tree[k].sum;return (query(k<<1,l,r)*query(k<<1|1,l,r))%mod; }int main() { // freopen("input.txt","r",stdin);int w;cin>>w;int kase=0;while(w--){int n;printf("Case #%d:\n",++kase);scanf("%d%d",&n,&mod);build(1,1,n);for(int i=1;i<=n;i++){int a,b;scanf("%d%d",&a,&b);if(a==1){update(1,i,b);printf("%lld\n",query(1,1,i));}else{update(1,b,1);printf("%lld\n",query(1,1,i));}}}return 0; }?
總結
以上是生活随笔為你收集整理的HDU - 5475 An easy problem(线段树)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: HDU - 2871 Memory Co
- 下一篇: HDU - 2795 Billboard