cf962(div3)

A. Legs

题意:有n条腿,鸡有两条,牛有四条,最少有几只动物

分析:判断牛最多几头,再判断是否有鸡

代码:

#include<bits/stdc++.h>
using namespace std;
void sol(){
    int n;cin>>n;
    if(n%4==0) cout<<n/4<<endl;
    else cout<<n/4+1<<endl;
}
int main(){
    int t;cin>>t;
    while(t--)sol();
}

B. Scale

题意:有n×n的网格,每k×k的网格里的格子都是一样的,将它变成一个网格

分析:枚举每个子网格,并更改即可

代码:

#include<bits/stdc++.h>
using namespace std;
void sol(){
    int n,k;cin>>n>>k;
    char a[n+10][n+10];
    for(int i=1;i<=n;i++){
        for(int j=1;j<=n;j++){
            cin>>a[i][j];
        }
    }
    int c=n/k;
    for(int i=1;i<=n;i+=k){
        for(int j=1;j<=n;j+=k){
            if(a[i][j]=='0')cout<<"0";
            else cout<<"1";
        }
        cout<<endl;
    }
}
int main(){
    int t;cin>>t;
    while(t--)sol();
}

C. Sort

题意:给定两个字符串a,b,区间l,r内a和b都从小到大排序,问需要几次操作(任选一个元素变成另一个元素)才能使区间lr内a和b完全相同

分析:元素一共只有26种,可以用二维数组读入。输出区间内的每个元素差值相加即可。

代码:

#include<bits/stdc++.h>
using namespace std;
void sol(){
    vector<vector<int>>cc;
    int n,q;cin>>n>>q;cc.resize(n+1,vector<int>(26,0));
    string a,b;cin>>a>>b;
    for(int i=1;i<=n;i++){
        cc[i]=cc[i-1];
        int c=a[i-1]-'a';
        int d=b[i-1]-'a';
        cc[i][c]++;
        cc[i][d]--;
    }
    while(q--){
        int l,r;cin>>l>>r;int sum=0;
        for(int i=0;i<26;i++){
            sum+=max(cc[r][i]-cc[l-1][i],0);    
        }
        cout<<sum<<endl;
    }
}
int main(){
    int t;cin>>t;
    while(t--)sol();
    return 0;
}

D. Fun

题意:找出满足ab+ac+bc<=n&&a+b+c<=x的a,b,c的个数

分析:遍历a,遍历符合条件的b,找出两个式子c的最大值的最小值相加。

代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
void sol(){
    int n,x;cin>>n>>x;ll ans=0;
    for(int a=1;a<=n;a++){
        for(int b=1;a+b<=x&&(ll)a*b<=n;b++){
            ans+=min(x-a-b,(n-a*b)/(a+b));
        }
    }
    cout<<ans<<endl;
}
int main(){
    int t;cin>>t;
    while(t--)sol();
    return 0;
}

E. Decode

题意:给定一个二进制字符串s,对于l,r的每对整数x,y,计算下x,y的对数个数,l,r中的0的数量等于x,y中的1的数量

分析:如果si=1,ai=1.如果si=0,ai=-1.用p表示a的前缀和数组。如果py-p(x-1)=0,就说明0和1的个数一样。lr的个数就是(n-i+1)*fx,fx为l可以取的值

代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll mod=1e9+7;
void sol(){
    string s;cin>>s;
    int n=s.size();
    s='#'+s;
    vector<ll>a(n+1);
    for(int i=1;i<=n;i++){
        if(s[i]=='1')a[i]=1;
        else a[i]=-1;
    }
    map<ll,ll>mp;
    mp[0]=1;
    int ans=0;ll sum=0;
    for(int i=1;i<=n;i++){
        sum+=a[i];
        ans+=(n-i+1)*mp[sum]%mod;
        ans%=mod;
        mp[sum]+=i+1;
    }
    cout<<ans<<endl;
}
int main(){
    int t;cin>>t;
    while(t--)sol();
    return 0;
}

F. Bomb

题意:给两个数组a和b,最初分数是0.每次操作可以任意加入一个ai并将ai变成max(0,ai-bi)。求最大分数。

分析:用二分找出一个数,这个数以上的数都要取。然后用等差数列求和将这些符合条件的加入,然后再减去多余操作的。

代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N=2e5+10;
ll a[N],b[N];int n;
ll f(ll x){
    ll sum=0;
    for(int i=1;i<=n;i++){
        if(a[i]<x)continue;
        sum+=(a[i]-x)/b[i]+1;
    }
    return sum;
}
void sol(){
    cin>>n;ll k;cin>>k;
    for(int i=1;i<=n;i++)cin>>a[i];
    for(int i=1;i<=n;i++)cin>>b[i];
    ll l=0,r=1e18;
    while(l+1<r){//找到一个数,从这个数以上的都要加入
        ll mid=(l+r)>>1;
        if(f(mid)<k)r=mid;
        else l=mid;
    }
    if(f(r)==k)l=r;
    r=l;
    ll ans=0,d=0;
    for(int i=1;i<=n;i++){
        if(a[i]<r)continue;
        ll v=(a[i]-r)/b[i]+1;
        ans+=a[i]*v-v*(v-1)*b[i]/2;
        d+=v;
    }
    cout<<ans-(d-k)*r<<endl;
    return;
    
}
int main(){
    int t;cin>>t;
    while(t--)sol();
    return 0;
}
  • 4
    点赞
  • 11
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值