Codeforces Round 1004 (Div. 2)


A. Adjacent Digit Sums

题意:求有没有一个数字各位和为x,并且加一后各位和为y

发现一个数加一后,要么和加一,要么进若干位,就是减若干个9然后加1。所以判断y==x+1||(xy+1)%9==0

点击查看代码
void solve() {
	int x, y;
	std::cin >> x >> y;
	if (y == x + 1 || (y < x) && (x - y + 1) % 9 == 0) {
		std::cout << "YES\n";
	} else {
		std::cout << "NO\n";
	}
}

B. Two Large Bags

题意:有两个袋子,开始第一个袋子有n个数,你每次可以给一个数给另一个袋子,或者选一个数使得两个袋子都至少有一个这个数然后让第一个袋子里的这个数加一。最后要让两个袋子的数相等。

发现值域和n同级别,于是可以开个数组记录每个数的出现次数。然后从小到大枚举,尽可能让数字加一。因为至少要一个袋子都有一个,所以每个数要留两个,其余的都加一,如果只有1个这个数,那么说明不可能有数变成它了,就是no。模拟即可。

点击查看代码
void solve() {
    int n;
    std::cin >> n;
    std::vector<int> a(n);
    for (int i = 0; i < n; ++ i) {
    	std::cin >> a[i];
    }

    std::vector<int> cnt(2 * n);
    for (int i = 0; i < n; ++ i) {
    	++ cnt[a[i]];
    }

    for (int i = 1; i < 2 * n; ++ i) {
    	if (cnt[i] == 1) {
    		std::cout << "NO\n";
    		return;
    	} else if (cnt[i] > 2) {
	    	cnt[i + 1] += cnt[i] - 2;
    	}
    }

    std::cout << "YES\n";
}

C. Devyatkino

题意:给你一个n,你每次可以给它加上一个各位都是9的数。求让n至少有一位是7的最少操作个数。

一个位置加上9其值一定会改变,发现6要加9次9能变成7,这是最多的情况,但考虑可能有进位的情况,可能需要加更多次。于是枚举加什么数,然后一直加每次判断n有没有出现7,记录最小次数就行。至于加多少次,应该不到10次,不过为了保险可以加20次。

点击查看代码
void solve() {
    i64 n;
    std::cin >> n;
    
    auto check = [&](i64 x) -> bool {
    	while (x) {
    		if (x % 10 == 7) {
    			return true;
    		}

    		x /= 10;
    	}

    	return false;
    };

    int ans = 100;
    for (i64 m = 9; m <= 1e17; m = m * 10 + 9) {
    	i64 x = n;
    	int sum = 0;
    	int t = 20;
    	while (t -- && !check(x)) {
    		x += m;
    		++ sum;
    	}

    	if (check(x)) {
    		ans = std::min(ans, sum);
    	}
    }

    std::cout << ans << "\n";
}

D. Object Identification

题意:交互题。给你值域为[1,n]的数组x,还隐藏了一个值域为[1,n]的数组y,没有一对x,y是相同的。有两种情况,一种是xiyi连有向边,一种是i代表坐标(xi,yi)。你不知道是哪种情况,你可以询问最多两次。每次问一个i,j,如果是第一种情况会返回ij的最短路,如果是第二种情况返回(xi,yi),(xj,yj)的曼哈顿距离。

先看有没有1到n的数没有出现,如果有则他没有出边,随便问一个点,如果是第一种情况答案肯定是0,否则是第二种情况。
如果都出现过,就记i,j记录1n出现的位置,然后询问1,nn,1,因为只有n条边,所以如果是情况一两个回答必有一个小于n1,否则是情况二。

点击查看代码
int ask(int i, int j) {
	std::cout << "? " << i << " " << j << std::endl;
	int res;
	std::cin >> res;
	return res;
}

void solve() {
    int n;
    std::cin >> n;
    std::vector<int> a(n);
    std::vector<int> st(n + 1);
    for (int i = 0; i < n; ++ i) {
    	std::cin >> a[i];
    }

    int p1 = 0, pn = 0;
    for (int i = 0; i < n; ++ i) {
    	st[a[i]] = 1;
    	
    	if (a[i] == 1) {
    		p1 = i + 1;
    	}

    	if (a[i] == n) {
    		pn = i + 1;
    	}
    }

    for (int i = 1; i <= n; ++ i) {
    	if (!st[i]) {
    		int j = 1;
    		while (j == i) {
    			++ j;
    		}

    		if (ask(i, j) == 0) {
				std::cout << "! A" << std::endl;
			} else {
				std::cout << "! B" << std::endl;
			}
			return;
    	}
    }

	if (ask(p1, pn) < n - 1 || ask(pn, p1) < n - 1) {
		std::cout << "! A" << std::endl;
	} else {
		std::cout << "! B" << std::endl;
	}
}

E. White Magic

题意:给你一个数组,你要选一个子序列a使得任意前缀的最小值大于等于其后缀的mex。问最多选几个数。

首先,只可能选一个0,不然如果一个0在前缀,一个0在后缀,必然不满足条件。
然后,如果不选0则可以选所有非0的数,因为任意后缀的mex=0。那么我们就需要就选了所有非0数后能不能再选一个0。发现如果0在后面,对所有后缀的mex的影响更大,所以应该尽可能让0在前面,于是求出所有后缀的mex,然后从前往后枚举,直到第一个0,使得这个0的前面的每个前缀最小值都大于等于后缀mex

点击查看代码
void solve() {
    int n;
    std::cin >> n;
    std::vector<int> a(n + 1);
    for (int i = 1; i <= n; ++ i) {
    	std::cin >> a[i];
    }

    std::vector<int> suf(n + 2);
    std::set<int> s;
    int mex = 0;
    for (int i = n; i ; -- i) {
    	s.insert(a[i]);
    	while (s.count(mex)) {
    		++ mex;
    	}

    	suf[i] = mex;
    }

    std::vector<int> pre(n + 1);
    pre[0] = 2e9;
    for (int i = 1; i <= n; ++ i) {
    	pre[i] = pre[i - 1];
    	if (a[i] != 0) {
    		pre[i] = std::min(pre[i], a[i]);
    	}
    }

    int ans = 0;
	bool flag = true;
    for (int i = 1; i <= n && a[i] != 0; ++ i) {
    	if (pre[i] < suf[i + 1]) {
    		flag = false;
    		break;
    	}
    }

    if (flag && mex > 0) {
    	++ ans;
    }

    for (int i = 1; i <= n; ++ i) {
    	ans += a[i] != 0;
    }

    std::cout << ans << "\n";
}
posted @   maburb  阅读(380)  评论(2编辑  收藏  举报
相关博文:
阅读排行:
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!
· AI技术革命,工作效率10个最佳AI工具
点击右上角即可分享
微信分享提示