题目链接:Dashboard - Codeforces Round #818 (Div. 2) - Codeforces
A - Madoka and Strange Thoughts
#include <bits/stdc++.h>
using namespace std;
#define inf 0x3f3f3f3f
#define lson l, mid, rt<<1
#define rson mid+1, r, rt<<1|1
typedef long long ll;
typedef unsigned long long ull;
const int mx = 5e3 + 10;
const int mod = 998244353;
typedef pair <int, int> pa;
int main() {
int t;
scanf("%d", &t);
while (t--) {
int n;
scanf("%d", &n);
ll ans = 0;
ans += n;
ans += n / 2 * 2;
ans += n / 3 * 2;
printf("%lld\n", ans);
}
return 0;
}
B - Madoka and Underground Competitions
#include <bits/stdc++.h>
using namespace std;
#define inf 0x3f3f3f3f
#define lson l, mid, rt<<1
#define rson mid+1, r, rt<<1|1
typedef long long ll;
typedef unsigned long long ull;
const int mx = 5e3 + 10;
const int mod = 998244353;
typedef pair <int, int> pa;
char str[mx][mx];
int main() {
int t;
scanf("%d", &t);
while (t--) {
int n,k,r,c;
scanf("%d%d%d%d", &n, &k, &r, &c);
int ii = (r - 1) % k + 1;
int jj = (c - 1) % k + 1;
vector <pa> vec;
vec.push_back(pa(ii, jj));
for (int i=1;i<=n;i++) {
for (int j=1;j<=n;j++) {
str[i][j] = '.';
}
str[i][n+1] = 0;
}
for (int i=r, j = c;;i++,j++) {
int u = i % k + 1;
int v = j % k + 1;
if (u == ii) break;
vec.push_back(pa(u, v));
}
for (pa temp: vec) {
int u = temp.first;
int v = temp.second;
for (int j=v; j<=n; j+=k)
for (int i=u; i<=n; i+=k) {
str[i][j] = 'X';
}
for (int j=u; j<=n; j+=k) {
for (int i=v; i<=n; i+=k) {
str[j][i] = 'X';
}
}
}
for (int i=1;i<=n;i++) {
printf("%s\n", str[i] + 1);
}
}
return 0;
}
C - Madoka and Formal Statement
解题思路:贪心。如果b[i] - b[i+1] > 1,那么就说明b[i]不能再增长了,这个时候如果a[i] != b[i],那么肯定是不行的,反之是可以的。
#include <bits/stdc++.h>
using namespace std;
#define inf 0x3f3f3f3f
#define lson l, mid, rt<<1
#define rson mid+1, r, rt<<1|1
typedef long long ll;
typedef unsigned long long ull;
const int mx = 2e5 + 10;
const int mod = 998244353;
typedef pair <int, int> pa;
int a[mx], b[mx];
int main() {
int t;
scanf("%d", &t);
while (t--) {
int n;
scanf("%d", &n);
for (int i=1;i<=n;i++)
scanf("%d", a + i);
for (int i=1;i<=n;i++)
scanf("%d", b + i);
int flag = 1;
for (int i=1;i<=n;i++) {
if (a[i] > b[i]) {
flag = 0;
break;
}
if (i == n) {
if (b[i] - b[1] > 1 && a[i] != b[i])
flag = 0;
} else {
if (b[i] - b[i+1] > 1 && a[i] != b[i])
flag = 0;
}
}
puts(flag? "YES":"NO");
}
return 0;
}
D - Madoka and The Corruption Scheme
解题思路:可以找规律,也可以推出来答案是。可知当i == k时,刚好为。
#include<bits/stdc++.h>
using namespace std;
#define inf 0x3f3f3f3f
#define lson l,mid,rt<<1
#define rson mid+1,r,(rt<<1)|1
typedef long long ll;
const int mx = 3e5 + 10;
const int mod = 1e9 + 7;
ll f[mx];
ll qpow(ll x, ll y) {
ll ans = 1;
while (y) {
if (y & 1) ans = ans * x % mod;
y >>= 1;
x = x * x % mod;
}
return ans;
}
int main() {
f[0] = 1;
for (int i=1;i<mx;i++) {
f[i] = i * f[i-1] % mod;
}
int n, k;
scanf("%d%d", &n, &k);
if (k >= n) {
printf("%lld\n", qpow(2, n));
return 0;
}
ll ans = 0;
for (int i=0; i<= k; i++) {
ll temp = qpow(f[n-i], mod-2) * qpow(f[i], mod-2) % mod;
ans += f[n] * temp % mod;
ans %= mod;
}
printf("%lld\n", ans);
return 0;
}
E - Madoka and The Best University
解题思路:求,我们假设a + b = j,那么c = n - j。去枚举gcd(a,b)的,令a = x,那么b= j - x, 如果gcd(x, j - x) = i,那么gcd(x/i, j/i) = 1,所以就是求和j互质的x有多少个,因为要除以i,根据欧拉函数可知,与j/i互质的有phi[j/i]个。最终答案就是 (n - j) * i / gcd(i, n - j) *phi[j/i]。时间复杂度为O( n * log(n) * log(n))
#include<bits/stdc++.h>
using namespace std;
#define inf 0x3f3f3f3f
#define lson l,mid,rt<<1
#define rson mid+1,r,(rt<<1)|1
typedef long long ll;
const int mx = 1e5 + 10;
const int mod = 1e9 + 7;
int phi[mx];
vector <int> pi;
bool vis[mx];
void init() {
phi[1] = 1;
for (int i=2;i<mx;i++) {
if (!vis[i]) {
pi.push_back(i);
phi[i] = i - 1;
}
for (int v: pi) {
if (i * v >= mx)
break;
vis[i * v] = 1;
if (i % v == 0) {
phi[i * v] = phi[i] * v;
break;
}
phi[i * v] = phi[i] * phi[v];
}
}
}
int main() {
init();
int n;
scanf("%d", &n);
ll ans = 0;
for (int i=1;i<=n;i++) {
for (int j=2*i; j<n;j+=i) {
ans += 1ll * (n-j) * i / __gcd(i, n-j) * phi[j/i];
ans %= mod;
}
}
printf("%lld\n", ans);
return 0;
}