HDU 6274 Master of Sequence(思維+樹狀陣列+二分)
題意:
給你n,m。
接下來n個數,給出a[i]。再接下來n個數,給出b[i]。
m次查詢,每次查詢:
若 id=1 則給出 x y 把a[i]的值修改為y。
若 id=2 則給出 x y 把b[i]的值修改為y。
若 id=3 則給出 k 求,其中
思路:
求S(t)>=k最小的t 顯然是二分。
注意S(t)這個式子。我們每次從1~n求的話,複雜度n*m會爆炸。
注意一個詭異的資料範圍:1<=ai<=1000
這是解決此題的關鍵!!!
我們將上式拆開得到t/ai 和 bi/ai 則可以O(n)求出。之後便可以O(1)修改了。
先確定答案為。然後看向下取整的影響。
而影響答案的只是 ,t%ai 和t%bi。不難發現,對於每個i,當t%ai<t%bi答案需要減1。
因此按a[i]建立1000個樹狀陣列,每個樹狀陣列維護分母為a[i],%a[i]>=x的數字個數即可。
同時預處理每個a[i]出現的次數,這樣總時間複雜度就降為O(T*m*1000*log(1000)*log(t))。
10s的時限,足以通過此題。如果還不懂,看程式碼就很容易理解了:
程式碼:
#include<bits/stdc++.h>
#define ll long long
#define inf 0x3f3f3f3f
using namespace std;
const int maxn=1010;
const int maxm=100010;
int n,m;
int lb(int x){return x&(-x);}
struct BIT
{
ll c[maxn];
void init(){memset(c,0,sizeof(c));}
void add(int i,int v)
{
while(i<maxn)
{
c[i]+=v;
i+=lb(i);
}
}
ll query(int i)
{
ll sum=0;
while(i>0)
{
sum+=c[i];
i-=lb(i);
}
return sum;
}
}bit[maxn];
ll sm,b[maxm],a[maxm];
ll cnt[maxn];
bool jud(ll x,ll y)
{
ll sum=0;
for(ll i=1;i<=1000;i++)
{
sum+=(x/i)*cnt[i]-(cnt[i]-bit[i].query(x%i+1));
if(sum>=y) return 1;
}
return 0;
}
int main()
{
int T,cas=1;
scanf("%d",&T);
while(T--)
{
scanf("%d%d",&n,&m);
memset(cnt,0,sizeof(cnt));
for(int i=1;i<=1000;i++)
bit[i].init();
for(int i=1;i<=n;i++)
{
scanf("%lld",&a[i]);
cnt[a[i]]++;
}
sm=0;
for(int i=1;i<=n;i++)
{
scanf("%lld",&b[i]);
sm+=(b[i]/a[i]);
bit[a[i]].add(b[i]%a[i]+1,1);
}
while(m--)
{
int id;
int x,y;
scanf("%d",&id);
if(id==1)
{
scanf("%d%d",&x,&y);
cnt[a[x]]--;
sm=sm-(b[x]/a[x])+(b[x]/(ll)y);
bit[a[x]].add(b[x]%a[x]+1,-1);
cnt[y]++;
bit[y].add(b[x]%y+1,1);
a[x]=y;
}
else if(id==2)
{
scanf("%d%d",&x,&y);
sm=sm-(b[x]/a[x])+((ll)y/a[x]);
bit[a[x]].add(b[x]%a[x]+1,-1);
bit[a[x]].add(y%a[x]+1,1);
b[x]=y;
}
else
{
ll y;
scanf("%lld",&y);
y+=sm;// !!!
ll l=0,r=1e15;
while(l<r)
{
ll mid=(l+r)>>1;
if(jud(mid,y)) r=mid;
else l=mid+1;
}
printf("%lld\n",r);
}
}
}
return 0;
}
相關文章
- HDU4843Wow! Such Sequence!(樹狀陣列寫法)陣列
- hdu 4368 樹狀陣列 離線維護陣列
- hdu 3874 樹狀陣列陣列
- HDU5147 Sequence II(樹狀陣列+字首和+字尾和)陣列
- hdu 5147 樹狀陣列陣列
- 二維樹狀陣列陣列
- hdu 4836 The Query on the Tree(線段樹or樹狀陣列)陣列
- HDU 1556 Color the ball(線段樹|樹狀陣列)陣列
- hdu4325 樹狀陣列+離散化陣列
- HDU 1166 敵兵佈陣 (樹狀陣列)陣列
- HDU 1166 敵兵佈陣(樹狀陣列)陣列
- HDU 2689 Sort it【樹狀陣列求逆序對】陣列
- HDU 1541 & POJ 2352 Stars (樹狀陣列)陣列
- HDU2689 Sort it (樹狀陣列求逆序數)陣列
- 樹狀陣列陣列
- 【二維樹狀陣列】poj 2155 Matrix陣列
- 二維樹狀陣列-poj2155陣列
- poj 1195 二維樹狀陣列陣列
- HDU5419Victor and Toys(樹狀陣列+數學期望)陣列
- HDU 1394 Minimum Inversion Number (樹狀陣列求逆序數)陣列
- 解析樹狀陣列陣列
- 二維樹狀陣列--poj1195陣列
- HDU 1556【區間更新+單點查詢 樹狀陣列】陣列
- [php]運用變數引用實現一維陣列轉多維樹狀陣列PHP變數陣列
- Codeforces Round #225 (Div. 2)(B思維題,E:dfs+樹狀陣列)陣列
- POJ 1195 Mobile phones(二維樹狀陣列)陣列
- HDU 5862 Counting Intersections(樹狀陣列+掃描線+離散化)陣列
- HDU4991 Ordered Subsequence (dp+樹狀陣列+離散化)陣列
- 樹狀陣列詳解陣列
- 樹狀陣列基礎陣列
- poj 2481 樹狀陣列陣列
- 【樹狀陣列 單點修改,區間求值】hdu 1166 敵兵佈陣陣列
- 字母統計(陣列思維)陣列
- 樹狀陣列模板題 & (樹狀陣列 1:單點修改,區間查詢)陣列
- 樹狀陣列和逆序對陣列
- 樹狀陣列快速入門陣列
- HNOI2016網路(整體二分+樹狀陣列)陣列
- HDU 1005 Number Sequence(矩陣)矩陣