Codeforces Round 924 (Div. 2)

文章介绍了四道Codeforces问题的解题思路,包括矩形分割条件判断、数组元素平等的二分查找、数列周期性的应用以及组合优化问题的枚举求解。
摘要由CSDN通过智能技术生成

A. Rectangle Cutting

题目链接:Problem - A - Codeforces

思路分析:

分类讨论,对于一个矩形,如果两个变都是奇数,不可分割重组,自然不会出现新矩形,如果只存在一个偶数边且偶数边的大小是技术变得二倍只有一种分割方法且分割重组之后的矩形河原来一样,不可行,其余可行;

代码

#include<iostream>
#include<algorithm>
using namespace std;

const int N = 1e5 + 10;

int n;

int main() {
    ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
    cin >> n;
    while(n--)
    {
        int a,b;
        cin >> a >>b;
        if(a<b)swap(a,b);
        if(a%2 && b%2)
        {
            cout<<"No"<<'\n';
        }
        else if(a==2*b && b%2)
        {
            cout<<"No"<<'\n';
        }
        else
            cout<<"Yes"<<'\n';
    }

}

B. Equalize

题目链接:Problem - B - Codeforces

思路分析:

枚举,先对原数组进行排序去重之后,以每个元素为起点二分查找找到最长的满足题意的子序列,比较即可,时间复杂度O(nlgn)

代码

#include<bits/stdc++.h>
using namespace std;

const int N = 2e5 + 10;
int n;
void solve()
{
    cin >> n;
    vector<int>a(n);
    for(int i = 0;i<n;i++)
        cin >> a[i];
    sort(a.begin(),a.end());
    a.erase(unique(a.begin(),a.end()),a.end());
    int ans = 0;
    for(int i = 0;i<a.size();i++)
    {
        int x = a[i] + n-1;
//        cout<<x<<endl;
        int u = upper_bound(a.begin(),a.end(),x)-a.begin()-i;
        ans = max(ans, u);
//        cout<<ans<<endl;
    }
    cout<<ans<<'\n';
}
int main() {
    ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
    int T;
    cin >>T;
    while(T--)solve();
}

C. Physical Education Lesson

题目链接:Problem - C - Codeforces

思路分析

通过观察可以发现原数列以(2*k-2)为一个周期,满足题意的位置有两类,一种是在上升区间找到的,另一种是在下降区间找到的,x-y和x+y-2的所有偶因数中大于2*k-2的数量

代码

#include<bits/stdc++.h>

using namespace std;
#define ll long long
const int N = 2e5 + 10;
int n;

set<ll> work(ll x,ll y) {
   set<ll>se;
   for(int i = 1;i*i<=x;i++)
   {
       if(x%i==0){
           if(i%2==0)se.insert(i);
           if(x/i%2==0)se.insert(x/i);
       }
   }
   for(int i = 1;i*i<=y;i++)
   {
       if(y%i==0){
           if(i%2==0)se.insert(i);
           if(y/i%2==0)se.insert(y/i);
       }
   }
   return se;
}

void solve() {
   ll x, y;
   cin >> x >> y;
   if (y > x) {
       cout << 0 << '\n';
       return;
   }
   ll u = 2*y-2;
   ll p = x-y,q = x+y-2;
   set<ll>se = work(p,q);
   ll ans = 0;
   for(auto i:se) {
//        cout<<i<<" ";
       if (i >= u)ans++;
   }
   cout<<ans<<'\n';
}

int main() {
   ios::sync_with_stdio(false), cin.tie(nullptr), cout.tie(nullptr);
   int T;
   cin >> T;
   while (T--)solve();
}

D. Lonely Mountain Dungeons

题目链接:Problem - D - Codeforces

思路分析

枚举分组数量,组合数计算之后比较即可。

代码

#include <iostream>
#include <vector>
#include <algorithm>
#define ll long long

using namespace std;

inline ll C(ll t) { return (t * (t - 1)) >> 1; }//计算C(n,2)

ll calc(ll s, ll t) {
    //s个人分成t组
    ll ret = C(t - s % t) * (s / t) * (s / t)
              + C(s % t) * (s / t + 1) * (s / t + 1)
              + (t - s % t) * (s % t) * (s / t) * (s / t + 1);
    return ret;
}

const int N = 2e5 + 5;
ll c[N], cnt[N];

void solve() {
    int n, b, x;
    ll sum = 0;
    cin >> n >> b >> x;
    for (int i = 1; i <= n; i++) cin >> c[i], sum = max(sum,c[i]), cnt[c[i]]++;
    //sum表示最大的组数
    sort(c + 1, c + 1 + n);
    n = unique(c + 1, c + 1 + n) - c - 1;
    ll ans = 0;
    for (int i = 1; i <= sum; i++) {//暴力枚举,找到兵力最大的分配组数
        ll tmp = 0;
        for (int j = 1; j <= n; j++) tmp += cnt[c[j]] * calc(c[j], i) * b;
        ans = max(ans, tmp - 1ll*(i - 1) * x);
    }
    for (int i = 1; i <= n; i++) cnt[c[i]] = 0;
    cout << ans << '\n';
}

int main() {
    int _;
    cin >> _;
    while (_--) solve();
    return 0;
}

  • 3
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值