The 9th Hebei Collegiate Programming Contest(A,D,F,H~K,M)
A.棋盘
思路:模拟,队友写的
#include<bits/stdc++.h>
#define ll long long
#define endl "\n"
using namespace std;
const int N=3e5;
ll a[N];
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
ll t;
cin>>t;
while(t--){
ll n;
cin>>n;
vector<ll>a(n+5),b(n+5);
for(ll i=1;i<=n;i++)cin>>a[i];
for(ll i=1;i<=n;i++)cin>>b[i];
ll flag=0;
if(n==1){
if(a[1]>b[1])flag=3;
else if(a[1]<b[1])flag=1;
else flag=2;
}
else if(n==2){
if(a[1]+a[2]>b[1]+b[2]||a[1]+b[1]>a[2]+b[2]) flag=3;
else if(a[1]+a[2]<b[1]+b[2]&&a[1]+b[1]<a[2]+b[2]) flag=1;
else flag=2;
}
else{
vector<ll>pre(n+4,0),sub(n+4,0);
//ll sum1=0,sum2=0;
ll sum=0;
ll flag1=0;
for(ll i=1;i<=n;i++){
pre[i]=pre[i-1]+a[i];
sub[i]=sub[i-1]+b[i];
sum+=(a[i]+b[i]);
}
//绝对赢
ll k=(n-1)/2;
if(pre[k]+sub[k]>sum-pre[k]-sub[k]){
cout << "Mandy" << endl;
continue;
}
if(sum-pre[n-k]-sub[n-k]>pre[n-k]+sub[n-k]){
cout << "brz" << endl;
continue;
}
//a可以平
if(pre[k]+sub[k]==sum-pre[k]-sub[k]){
flag=max(flag,2ll);
}
//b可以平
if(sum-pre[n-k]-sub[n-k]==pre[n-k]+sub[n-k]){
flag1=1;
}
//n为偶数,回头
if(n%2==0){
if(pre[n/2]+sub[n/2]>sum-pre[n/2]-sub[n/2]){
flag=max(flag,3ll);
}
else if(pre[n/2]+sub[n/2]==sum-pre[n/2]-sub[n/2]){
flag=max(flag,2ll);
}
else flag=max(flag,1ll);
}
//A走第一行
if(pre[n]>sub[n]){
flag=max(flag,3ll);
}
else if(pre[n]==sub[n]){
flag=max(flag,2ll);
}
else{
flag=max(flag,1ll);
}
if(flag1){
flag=min(flag,2ll);
}
}
if(flag==3){
cout << "Mandy" << endl;
}
else if(flag==2){
cout << "draw" << endl;
}
else{
cout << "brz" << endl;
}
}
}
D.金麦园
思路:二分极限范围,然后再统计即可,注意二分里面用队列或者双指针维护,不能nlognlogn
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
#define ll long long
const int INF=0x3f3f3f3f;
const int N=2468;
const ll mod=1e9+7;
void fio(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
signed main()
{
fio();
ll t=1;
while(t--)
{
ll n,k;
cin>>n>>k;
vector<ll>a(n+5),pre(n+5,0);
for(ll i=1;i<=n;i++)cin>>a[i];
sort(a.begin()+1,a.begin()+1+n);
for(ll i=1;i<=n;i++){
pre[i]=pre[i-1]+a[i];
}
ll l=1,r=a[n]-a[1];
function<ll(ll)>ck=[&](ll x){
ll cnt=0;
queue<ll>f;
for(ll i=1;i<=n;i++){
if(f.empty()){
f.push(a[i]);
}
else {
while(!f.empty()&&f.front()<a[i]-x){
cnt+=f.size()-1;
f.pop();
}
f.push(a[i]);
}
}
while(!f.empty()){
cnt+=f.size()-1;
f.pop();
}
if(cnt>=k)return 1ll;
else return 0ll;
};
while(l<r){
ll mid=l+r>>1;
if(ck(mid))r=mid;
else l=mid+1;
}
ll cnt=0;
ll ans=0;
for(ll i=1;i<=n;i++){
ll d=a[i]+r-1;
ll j=upper_bound(a.begin()+1+i,a.begin()+1+n,d)-a.begin();
j--;
if(j<=i)continue;
else {
cnt+=j-i;
ans+=(pre[j]-pre[i])-a[i]*(j-i);
}
}
ans+=(k-cnt)*r;
cout<<ans<<endl;
}
return 0;
}
F.不死国的生命树
思路:类似倍增lca,直接套用倍增形式即可,然后用正常深度维护倍增点
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
#define ll int
const int INF=0x3f3f3f3f;
const int N=2468;
const ll mod=1e9+7;
void fio(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
ll fa[2500000][36];
ll dep[2500000];
signed main()
{
fio();
ll t=1;
while(t--)
{
ll n;
cin>>n;
vector<ll>a(n+5);
for(ll i=1;i<=n;i++){
cin>>a[i];
}
vector<ll>g[n+5];
for(ll i=2;i<=n;i++){
ll x;
cin>>x;
g[x].push_back(i);
}
vector<ll>vis(n+4,0);
function<void(ll,ll)>dfs=[&](ll x,ll z){
ll f=vis[a[x]+1];
fa[x][0]=f;
dep[x]=dep[z]+1;
ll d=vis[a[x]];
vis[a[x]]=x;
for(ll i=1;i<=32;i++){
fa[x][i]=fa[fa[x][i-1]][i-1];
}
for(auto j:g[x]){
dfs(j,x);
}
vis[a[x]]=d;
};
dfs(1,0);
function<ll(ll,ll)>lca=[&](ll x,ll sd){
ll u=a[x];
for(ll i=32;i>=0;i--){
if(dep[fa[x][i]]>=sd)x=fa[x][i];
}
return abs(u-a[x])+1;
};
ll q;cin>>q;
while(q--){
ll l,r;
cin>>l>>r;
r=dep[r];
cout<<lca(l,r)<<endl;
}
}
return 0;
}
H.What is all you need?
思路:签到,无需多言
#include<bits/stdc++.h>
#define ll long long
using namespace std;
int main(){
string f;
cin>>f;
ll j=f.size()-1-11;
string k=f.substr(j,12);
if(k=="isallyouneed"){
cout<<"Yes"<<endl;
cout<<f.substr(0,f.size()-12)<<endl;
}
else cout<<"No"<<endl;
}
I.感染
思路:换根dp,每次换根,可以认为变短的少扩散了一轮,变长的多扩了一轮
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
#define ll long long
const int INF=0x3f3f3f3f;
const int N=2468;
const ll mod=1e9+7;
void fio(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
signed main()
{
fio();
ll t=1;
cin>>t;
while(t--)
{
ll n;
cin>>n;
vector<ll>g[n+5];
for(ll i=1;i<n;i++){
ll l,r;
cin>>l>>r;
g[l].push_back(r);
g[r].push_back(l);
}
vector<ll>dep(n+4,0),sd(n+4,0),sz(n+4,0);
function<void(ll,ll,ll)>dfs=[&](ll x,ll f,ll cs){
// sd[x]=cs;
sz[x]=1;
// dep[x]=dep[f]+1;
for(auto j:g[x]){
if(f==j)continue;
// sda[x]=max(sd[x],dfs(j,x,cs+1));
// sz[x]+=sz[j];
dfs(j,x,cs+1);
sz[x]+=sz[j];
}
// return sd[x];
};
dfs(1,0,0);
ll maxn=-1e18;
vector<ll>ans;
function<void(ll,ll,ll)>ck=[&](ll x,ll f,ll v){
if(maxn<v){
ans.clear();
maxn=v;
ans.push_back(x);
}
else if(maxn==v)ans.push_back(x);
for(auto j:g[x]){
if(j==f)continue;
sz[x]-=sz[j];
ll u=sz[j];
sz[j]+=sz[x];
ck(j,x,v+u-sz[x]);
sz[j]-=sz[x];
sz[x]+=sz[j];
}
};
ck(1,0,0);
cout<<ans.size()<<endl;
sort(ans.begin(),ans.end());
for(auto j:ans)cout<<j<<" ";
cout<<endl;
}
return 0;
}
J.Generate 01 String
思路:用栈简单维护即可
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
#define ll long long
const int INF=0x3f3f3f3f;
const int N=2468;
const ll mod=1e9+7;
void fio(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
ll ksm(ll a,ll b){
ll res=1;
while(b){
if(b&1){
res*=a;
res%=mod;
}
a*=a;
a%=mod;
b>>=1;
}
return res%mod;
}
pair<ll,ll>k[N][N][2];//n条线段对于m个点的斜率
vector<int> posi[N];//n个线段对于点的排序
pair<ll,ll>seg[N];
pair<ll,ll> poi[N];
int now;
int jd(pair<ll,ll>&a1,pair<ll,ll>&a2){
if(a1.first*a2.second<a2.first*a1.second){
return -1;
}
else if(a1.first*a2.second>a2.first*a1.second) {
return 1;
}
return 0;
}
bool cmp(int &a,int &b){
if(k[now][a][0]!=k[now][b][0]){
return k[now][a][0].first*k[now][b][0].second<k[now][b][0].first*k[now][a][0].second;
}
return k[now][a][1].first*k[now][b][1].second>k[now][b][1].first*k[now][a][1].second;
}
signed main()
{
fio();
ll t=1;
while(t--)
{
string s;
cin>>s;
stack<char>st;
int zero=0,one=0;
for(int i=0;i<s.length();i++){
zero+=s[i]=='0';
one+=s[i]=='1';
}
if(zero!=one){
cout<<"-1"<<endl;
}else{
cout<<s.length()/2<<endl;
int now=1;
for(int i=0;i<s.length();i++){
if(st.empty()){
if(s[i]=='0'){
cout<<now<<" "<<"1"<<endl;
}else{
cout<<now<<" 2"<<endl;
}
st.push(s[i]);
}else{
if(st.top()==s[i]){
st.push(s[i]);
if(s[i]=='0'){
cout<<now<<" "<<"1"<<endl;
}else{
cout<<now<<" 2"<<endl;
}
}else{
now++;
st.pop();
}
}
}
}
}
return 0;
}
K.UNO!
思路:用数组模拟链表维护,队友写的
#include<bits/stdc++.h>
#define ll long long
#define endl "\n"
using namespace std;
const int N=3e5;
int pre[N][2];//0往前1往后
ll a[N];
int main(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
int n,m;
cin>>n>>m;
for(int i=0;i<n;i++){
pre[i][0]=(i-1+n)%n;
pre[i][1]=(i+1)%n;
}
// for(int i=0;i<n;i++){cout<<pre[i][0]<<" "<<pre[i][1]<<"\n";}
for(int i=0;i<n;i++){
cin>>a[i];
}
string s;
cin>>s;
int jd=1,now=0;
for(int j=0;j<m;j++){
if(s[j]=='C'){
a[now]--;
if(a[now]==0){
int nxt=pre[now][1];
int prr=pre[now][0];
pre[nxt][0]=prr;
pre[prr][1]=nxt;
}
}else if(s[j]=='S'){
a[now]--;
if(a[now]==0){
int nxt=pre[now][1];
int prr=pre[now][0];
pre[nxt][0]=prr;
pre[prr][1]=nxt;
}
now=pre[now][jd];//禁止
now+=n;
now%=n;
}else if(s[j]=='R'){
a[now]--;
if(a[now]==0){
int nxt=pre[now][1];
int prr=pre[now][0];
pre[nxt][0]=prr;
pre[prr][1]=nxt;
}
jd=1-jd;
}else{//'D'
a[now]--;
if(a[now]==0){
int nxt=pre[now][1];
int prr=pre[now][0];
pre[nxt][0]=prr;
pre[prr][1]=nxt;
}
now=pre[now][jd];//禁止
now+=n;
now%=n;
a[now]+=2;
}
now=pre[now][jd];
now+=n;
now%=n;
}
for(int i=0;i<n;i++){
cout<<a[i]<<"\n";
}
}
M.第九届河北省大学生程序设计竞赛
思路:二进制枚举
#include<bits/stdc++.h>
#define endl '\n'
using namespace std;
#define ll long long
const int INF=0x3f3f3f3f;
const int N=2468;
const ll mod=1e9+7;
void fio(){
ios::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
}
signed main()
{
fio();
ll t=1;
while(t--)
{
ll n,m;
cin>>n>>m;
string f[m+5];
ll flag=0;
for(ll i=1;i<=m;i++)cin>>f[i],f[i]='0'+f[i];
vector<bool>vis(n+5,0);
vector<ll>a(4,0),b(4,0);
for(ll i=1;i<=3;i++)cin>>a[i];
for(ll i=1;i<=3;i++)cin>>b[i];
for(ll i=1;i<=(1ll<<n)-1;i++){
ll cnt=0;
for(ll j=0;j<n;j++){
vis[j+1]=0;
if((1ll<<j)&i){
cnt++;
vis[j+1]=1;
}
}
if(cnt>=10&&cnt<=13){
vector<ll>cn(m+4,0);
for(ll j=1;j<=m;j++){
for(ll d=1;d<=n;d++){
if(f[j][d]=='1'&&vis[d]==1){
cn[j]++;
}
}
}
sort(cn.begin()+1,cn.begin()+1+m);
if(cn[m-a[1]+1]==b[1]&&cn[m-a[2]+1]==b[2]&&cn[m-a[3]+1]==b[3]){
flag=cnt;
break;
}
}
}
if(flag==0)cout<<-1<<endl;
else {
cout<<flag<<endl;
for(ll j=1;j<=n;j++){
if(vis[j])cout<<j<<" ";
}
cout<<endl;
}
}
return 0;
}

浙公网安备 33010602011771号