牛客周赛 Round 49

写在前面

代码需要手动展开!!!

A题

按题目输出即可
但是要注意会爆int

点击查看代码
#include<bits/stdc++.h>
#define all(x) (x).begin(), (x).end()
#define fi first
#define se second
#define lowbit(x) (x) & (-x)
using i64 = long long;
using pii = std::pair<int, int>;
void solve()
{
    i64 a, b;
    std::cin >> a >> b;
    std::cout << (a - b) - b * 10;
}
int main()
{
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    std::ios::sync_with_stdio(false);
    int T = 1;
    //std::cin >> T;
    while (T --) solve();
    return 0;
}

B题

二进制位数相当于某个数可以分解的次数
我们从最高位进行分解
用一个now,记录当前位数的史莱姆有多少个
将所有now加起来既可

点击查看代码
#include<bits/stdc++.h>
#define all(x) (x).begin(), (x).end()
#define fi first
#define se second
#define lowbit(x) (x) & (-x)
using i64 = long long;
using pii = std::pair<int, int>;
void solve()
{
    int h;
    std::cin >> h;
    int cnt = 0;
    int x = h;
    while (x) {
    	x /= 2;
    	cnt ++;
    }
    int now = 1;
    int res = 0;
    while (cnt --) {
    	res += now;
    	now *= 2;
    }
    std::cout << res << '\n';
}
int main()
{
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    std::ios::sync_with_stdio(false);
    int T = 1;
    //std::cin >> T;
    while (T --) solve();
    return 0;
}

C题

利用贪心的思想
用一个sum维护当前段的总和
如果当前段的sum已经小于0了,那么这一段对后面做的一定是负贡献
那么这一段就应该舍去,即sum等于0,开始一段新的
然后每步取max即可得到最终答案

点击查看代码
#include<bits/stdc++.h>
#define int long long
#define all(x) (x).begin(), (x).end()
#define fi first
#define se second
#define lowbit(x) (x) & (-x)
using i64 = long long;
using pii = std::pair<int, int>;
void solve()
{
    int n, x;
    std::cin >> n >> x;
    std::vector<int> a(n);
    for (int i = 0; i < n; i ++) {
    	std::cin >> a[i];
    	a[i] -= x;
    }
    int ans = 0;
    int sum = 0;
    for (int i = 0; i < n; i ++) {
    	sum += a[i];
    	if (sum < 0) {
    		sum = 0;
    	}
    	ans = std::max(ans, sum);
    }
    std::cout << ans << '\n';
}
signed main()
{
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    std::ios::sync_with_stdio(false);
    int T = 1;
    //std::cin >> T;
    while (T --) solve();
    return 0;
}

D题

根据前缀异或和的思想
设1 ~ i的异或和是s[i]
可以得到答案是s[r] ^ s[l - 1]
因为l, r最大都是1e18,直接进行预处理会T
所以我们应该快速算出来某个数x的s[x]
根据打表
x % 4 == 0时,1~x的异或和是x
x % 4 == 1时,1~x的异或和是1
x % 4 == 2时,1~x的异或和是x + 1
x % 4 == 3时,1~x的异或和是0

点击查看代码
#include<bits/stdc++.h>
#define all(x) (x).begin(), (x).end()
#define fi first
#define se second
#define lowbit(x) (x) & (-x)
using i64 = long long;
using pii = std::pair<int, int>;
void solve()
{
	i64 l, r;
	std::cin >> l >> r;
	auto calc = [&](i64 x) -> i64 {
		if (x % 4 == 0) {
			return x;
		}
		else if (x % 4 == 1) {
			return 1;
		}
		else if (x % 4 == 2) {
			return x + 1;
		}
		else {
			return 0;
		}
	};
	std::cout << (calc(r) ^ calc(l - 1)) << '\n';
}
int main()
{
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    std::ios::sync_with_stdio(false);
    int T = 1;
    std::cin >> T;
    while (T --) solve();
    return 0;
}

E题

将第一个式子的y,带入第二个式子
可以求得a1 * b2 * x^2 + (b1 * b2 + a2) * x + (c1 * b2 + c2) = 0
然后分类讨论一下答案即可
对于新的一元二次方程
a = a1 * b2
b = b1 * b2 + a2
c = c1 * b2 + c2
detla = b * b - 4 * a * c
当a == 0 and b == 0 and c == 0时, 此时解有无限个
当a == 0 and b == 0 and c != 0时,此时无解
当a == 0 and b != 0时,这时是一元一次方程,此时解有一个

当detla < 0时,此时无解
当detla == 0时,此时只有一个解
当detla > 0时,此时有两个解

注意会爆long long
C++得用__int128
我这里直接用的python

点击查看代码
import math
t = int(input())
def solve():
	a1, b1, c1, a2, b2, c2 = list(map(int, input().split()))
	a = a1 * b2
	b = b1 * b2 + a2
	c = c1 * b2 + c2
	detla = b * b - 4 * a * c
	if (a == 0):
		if (b == 0):
			if (c == 0):
				print("INF")
			else:
				print(0)
		else:
			print(1)
	else:
		if detla < 0: 
			print(0)
		elif detla == 0:
			print(1)
		else:
			print(2)
for _ in range(0, t):
	solve()

F题

字符串哈希
h[1, n - 2 * k] + h[2 * k + 1, n] == 2 * h[k + 1, n - k]

点击查看代码
#include<bits/stdc++.h>
#define all(x) (x).begin(), (x).end()
#define fi first
#define se second
#define lowbit(x) (x) & (-x)
using i64 = long long;
using pii = std::pair<int, int>;
using u64 = unsigned long long;
bool isprime(int n) {
    if (n <= 1) {
        return false;
    }
    for (int i = 2; i * i <= n; i++) {
        if (n % i == 0) {
            return false;
        }
    }
    return true;
}

int findPrime(int n) {
    while (!isprime(n)) {
        n++;
    }
    return n;
}
void solve()
{
    std::mt19937 rng(std::chrono::steady_clock::now().time_since_epoch().count());
    const int P = findPrime(rng() % 900000000 + 100000000);
    int n;
    std::cin >> n;
    std::vector<int> a(n);
    for (int i = 0; i < n; i ++) {
        std::cin >> a[i];
    }
    std::vector<u64> p(n + 1), h(n + 1);
    p[0] = 1;
    for (int i = 0; i < n; i ++) {
        p[i + 1] = p[i] * P;
        h[i + 1] = h[i] * P + a[i];
    } 
    auto find = [&](int l, int r) -> u64{
        return h[r] - h[l - 1] * p[r - l + 1];
    };
    for (int k = 1; k <= n; k ++) {
        if (find(1, n - 2 * k) + find(2 * k + 1, n) == 2 * find(k + 1, n - k)) {
            std::cout << k << '\n';
            return;
        }
    }
}
int main()
{
    std::cin.tie(nullptr);
    std::cout.tie(nullptr);
    std::ios::sync_with_stdio(false);
    int T = 1;
    //std::cin >> T;
    while (T --) solve();
    return 0;
}
posted @ 2024-06-30 23:52  KXDdesu  阅读(60)  评论(0编辑  收藏  举报