首页 > 其他分享 >ABC355 A ~ D

ABC355 A ~ D

时间:2024-05-25 23:01:44浏览次数:12  
标签:gt const int ll while ch ABC355

A

可能写麻烦了,但是至少它对了。

#include <bits/stdc++.h>
#define gt getchar
#define pt putchar

typedef long long ll;
const int MAXN = 2e5 + 5;
const int mod = 998244353;

ll read() {
	ll x = 0, f = 1;char ch = gt();
	while (ch < '0' || ch > '9') {if (ch == '-') f = -1;ch = gt();}
	while (ch >= '0' && ch <= '9') {x *= 10;x += ch - '0';ch = gt();}
	return x * f;
}

ll a[5];

int main() {
	a[read()] = a[read()] = 1;
	ll res = 0;
	for (int i = 1; i <= 3; i++) {
		if(a[i] == 0) {
			if(res == 0) res = i;
			else {
				std::cout << -1;
				return 0;
			}
		}
	}
	std::cout << res;
	return 0;
}

B

\(f_i\) 表示 \(i\) 在 \(a\) 中是否出现过。

搞到一起之后排序,判断即可。

#include <bits/stdc++.h>
#define gt getchar
#define pt putchar

typedef long long ll;
const int MAXN = 2e5 + 5;
const int mod = 998244353;

ll read() {
	ll x = 0, f = 1;char ch = gt();
	while (ch < '0' || ch > '9') {if (ch == '-') f = -1;ch = gt();}
	while (ch >= '0' && ch <= '9') {x *= 10;x += ch - '0';ch = gt();}
	return x * f;
}

ll a[MAXN], b[MAXN], c[MAXN];
bool f[MAXN];

int main() {
	ll n = read(), m = read();
	for (int i = 1; i <= n; i++) {
		a[i] = read();
		c[i] = a[i];
		f[a[i]] = true;
	}
	for (int i = 1; i <= m; i++) {
		b[i] = read();
		c[i + n] = b[i];
	}
	ll len = n + m;
	std::sort(c + 1, c + len + 1);
	for (int i = 1; i < len; i++) {
		if(f[c[i]] && f[c[i + 1]]) {
			puts("Yes");
			return 0;
		}
	}
	puts("No");
	return 0;
}

C

\(hang_i\) 表示第 \(i\) 行被涂的格子的个数。

\(lie_i\) 表示第 \(i\) 列被涂的格子的个数。

\(xie1,xie2\) 表示两条对角线上被涂的格子的个数。

行和列都好处理,对角线可以通过 \(O(n)\) 预处理。

#include <bits/stdc++.h>
#define gt getchar
#define pt putchar

typedef long long ll;
const int MAXN = 4e6 + 5;
const int mod = 998244353;

ll read() {
	ll x = 0, f = 1;char ch = gt();
	while (ch < '0' || ch > '9') {if (ch == '-') f = -1;ch = gt();}
	while (ch >= '0' && ch <= '9') {x *= 10;x += ch - '0';ch = gt();}
	return x * f;
}

ll hang[MAXN], lie[MAXN];
ll dui1, dui2;
bool f[MAXN], g[MAXN];
//f左上-右下对角线经过的数值
//g右上-坐下对角线经过的数值

int main() {
	ll n = read(), t = read();
	ll ans = 0;
	for (int i = 1; i <= n; i++) {
		f[(i - 1) * n + i] = true;
		g[i * n - i + 1] = true;
		//预处理
	}
	for (int i = 1; i <= t; i++) {
		ll a = read();
		if(ans) continue;
		ll nowhang;
		if(a % n == 0) nowhang = a / n;
		else nowhang = a / n + 1;
		ll nowlie;
		if(a % n != 0) nowlie = a % n;
		else nowlie = n;
		//当前这个数在第几行、第几列
		hang[nowhang]++;
		if(hang[nowhang] == n) {
			ans = i;
			continue;
		}
		lie[nowlie]++;
		if(lie[nowlie] == n) {
			ans = i;
			continue;
		}
		//边改变当前行的数值边判断
		if(f[a]) {
			dui1++;
			if(dui1 == n) {
				ans = i;
				continue;
			}
		}
		if(g[a]) {
			dui2++;
			if(dui2 == n) {
				ans = i;
				continue;
			}
		}
		//对角线
	}
	std::cout << (ans == 0 ? -1 : ans);
	return 0;
}

D

按照左端点排序,左端点相同就按照右端点排序。

枚举 \(1\sim n\),二分找到 \(i\) 后面的区间第一个 \(j\) 满足 \(l_j > r_i\),也就是这两个区间没有重合,把答案增加 \(j - 1 - i\)。

不用考虑 \(i\) 前面的区间,因为在考虑位置 \(<i\) 的线段的时候已经考虑过了。

警钟长鸣,不要忘记删 std::cerr 调试语句!

#include <bits/stdc++.h>
#define gt getchar
#define pt putchar

typedef long long ll;
const int MAXN = 5e5 + 5;
const int mod = 998244353;

ll read() {
	ll x = 0, f = 1;char ch = gt();
	while (ch < '0' || ch > '9') {if (ch == '-') f = -1;ch = gt();}
	while (ch >= '0' && ch <= '9') {x *= 10;x += ch - '0';ch = gt();}
	return x * f;
}

ll n;
std::pair<ll, ll> a[MAXN];
ll c[MAXN];

int main() {
	n = read();
	for (int i = 1; i <= n; i++) {
		a[i].first = read();
		a[i].second = read();
	}
	std::sort(a + 1, a + n + 1);
	ll res = 0;
	for (int i = 1; i <= n; i++) c[i] = a[i].first;//为了方便二分,用 c 储存排序后的 l[i]
	for (int i = 1; i < n; i++) {
		ll p = std::upper_bound(c + i + 1, c + n + 1, a[i].second) - c;
		res += p - 1 - i;
	}
	std::cout << res << '\n';
	return 0;
}

标签:gt,const,int,ll,while,ch,ABC355
From: https://www.cnblogs.com/ljlbj-fengyuwuzu/p/18213128

相关文章

  • ABC355 D
    D-IntersectingIntervals我们思考如何计算不交的线段数量首先总的线段如果全部相交那么线段数应为n*(n-1)/2那么对于每对r[i]<l[i]都为不交的线段所以我们需要计算不交的线段数同时删去自己本身点击查看代码#include<bits/stdc++.h>#defineintlonglong#defineall(......