牛客练习赛 58——树链剖分
生活随笔
收集整理的這篇文章主要介紹了
牛客练习赛 58——树链剖分
小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.
A - 牛能和寶石
簽到題
#define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<iostream> #include<algorithm> using namespace std; const int N=100010; int a[N],b[N]; int n; int main() {IO;int T=1;//cin>>T;while(T--){cin>>n;for(int i=1;i<=n;i++) cin>>a[i];for(int i=1;i<=n;i++) cin>>b[i];sort(a+1,a+1+n);sort(b+1,b+1+n);int res=0;for(int i=1;i<=n;i++) res=max(res,a[i]+b[n-i+1]);cout<<res<<'\n';}return 0;}B - 牛妹和01串
簽到題
#define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<iostream> #include<algorithm> using namespace std; const int N=100010; int a[N],b[N]; int n; int main() {IO;int T=1;//cin>>T;while(T--){string s;cin>>s;int res=0,cnt0=0,cnt1=0;for(auto t:s){if(t=='1') cnt1++;if(t=='0') cnt0++;if(cnt0&&cnt1){res++;cnt0=0;cnt1=0;}}cout<<res<<'\n';}return 0; }C - 矩陣消除游戲
m,nm,nm,n很小考慮直接枚舉
行列都枚舉會TLE,考慮優(yōu)化:如果行確定那么選擇列可以貪心。
TLE代碼——枚舉行列
//lajiTLE代碼 #define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<iostream> #include<algorithm> using namespace std; typedef long long ll; typedef pair<int,int> pii; const int N=20; int a[N][N]; int n,m,k; vector<int> state[N]; int lowbit(int x) {return x&-x; } int calc(int x) {int res=0;while(x){x-=lowbit(x);res++;}return res; } ll solve(int r,int c) {ll res=0;for(int i=0;i<n;i++)for(int j=0;j<m;j++)if((r>>i&1)||(c>>j&1)) res+=a[i][j];return res; } int main() {IO;int T=1;//cin>>T;while(T--){cin>>n>>m>>k;for(int i=0;i<n;i++) for(int j=0;j<m;j++) cin>>a[i][j];k=min(k,min(n,m));for(int i=0;i<1<<min(n,m);i++) state[calc(i)].push_back(i);ll res=0;for(int r=0;r<=k;r++){int c=k-r;for(int i=0;i<state[r].size();i++){int nowr=state[r][i];for(int j=0;j<state[c].size();j++){int nowc=state[c][j];res=max(res,solve(nowr,nowc));}}}cout<<res<<'\n';}return 0;}AC代碼——枚舉行貪心列
#define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<iostream> #include<algorithm> using namespace std; typedef long long ll; typedef pair<int,int> pii; const int N=20; int a[N][N]; int n,m,k; vector<int> state[N]; int lowbit(int x) {return x&-x; } int calc(int x) {int res=0;while(x){x-=lowbit(x);res++;}return res; } int b[N]; ll solve(int row,int cnt) {ll res=0;for(int j=0;j<m;j++){b[j]=0;for(int i=0;i<n;i++){if(row>>i&1) continue;b[j]+=a[i][j];}}sort(b,b+m);reverse(b,b+m);for(int i=0;i<n;i++)if(row>>i&1)for(int j=0;j<m;j++) res+=a[i][j];for(int i=0;i<cnt;i++)res+=b[i];return res; } int main() {IO;int T=1;//cin>>T;while(T--){cin>>n>>m>>k;for(int i=0;i<n;i++) for(int j=0;j<m;j++) cin>>a[i][j];k=min(k,min(n,m));for(int i=0;i<1<<min(n,m);i++) state[calc(i)].push_back(i);ll res=0;for(int r=0;r<=k;r++){int c=k-r;for(int i=0;i<state[r].size();i++){int nowr=state[r][i];res=max(res,solve(nowr,c));}}cout<<res<<'\n';}return 0;}D - 迷宮
題解好像是dp做的,我dijkstra瞎搞出來了。
分析題目不難知道向上走和向左走沒什么用,于是只考慮向右走和向下走
向右走的代價為0(不需要堵路)。
如果能向右走,那么如果在該點向下走那么就要花費1代價(堵路),否則向下走的代價為0。
E - 最大GCD
首先暴力把每個aia_iai?的約數(shù)搞出來,用一個vector存儲一下,d[i]d[i]d[i]表示存在約數(shù)是iii的aia_iai?所在的位置下標。詢問同樣先把所有約數(shù)搞出來,然后逆序去vector<int> d[]二分查找看看是否在所給區(qū)間內即可。
#define IO ios::sync_with_stdio(false);cin.tie();cout.tie(0) #pragma GCC optimize(2) #include<vector> #include<iostream> #include<algorithm> using namespace std; const int N=100010; int n,m; vector<int> d[N]; int main() {//IO;int T=1;//cin>>T;while(T--){cin>>n>>m;for(int i=1;i<=n;i++){int a;cin>>a;for(int j=1;j<=a/j;j++){if(a%j) continue;d[j].push_back(i);if(j!=a/j) d[a/j].push_back(i);}}while(m--){int l,r,x;cin>>l>>r>>x;vector<int> dx;for(int i=1;i<=x/i;i++){if(x%i) continue;dx.push_back(i);if(i!=x/i) dx.push_back(x/i);}sort(dx.begin(),dx.end());reverse(dx.begin(),dx.end());for(auto t:dx){if(!d[t].size()) continue;int lnow=lower_bound(d[t].begin(),d[t].end(),l)-d[t].begin();if(lnow>=d[t].size()) continue;if(d[t][lnow]<=r) {cout<<t<<'\n';break;}}}}return 0;}F - XOR TREE
分析一下不難發(fā)現(xiàn)每個點對答案的貢獻有以下規(guī)律:
- 如果路徑點數(shù)是奇數(shù)個點,那么等效于所有偶數(shù)次序的點被記錄一次
- 如果路徑點數(shù)是偶數(shù)個點,那么所有點都被計入一次
①路徑點數(shù)可以根據(jù)求樹上路徑距離間接求得
②對于一條路徑上的奇偶點,可以根據(jù)端點的奇偶性+深度的奇偶性來確定。
因此樹剖后根據(jù)dfs序建立兩棵線段樹分別維護深度是奇數(shù)和深度是偶數(shù)點的區(qū)間異或值。
查詢和修改的時候只需要分類討論以下即可。
要加油哦~
總結
以上是生活随笔為你收集整理的牛客练习赛 58——树链剖分的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 最实用的电脑桌最舒服的电脑桌
- 下一篇: 牛客练习赛 57——manacher算法