Codeforces Round #779 (Div. 2)

比赛链接

大佬饶命只有 前四个

A. Marin and Photoshoot

题意:给你一个01字符串,你可以在任意一个位置插入0或者1,但是最终要任意长度超过两个的子串中1的个数比0的个数多, 问最小需要几次操作

 思路:保证任意两个0之间至少有两个一即可

AC代码

#include<iostream>
#include<algorithm>
#include<cmath>
#include<deque>
#include<string>
#include<cstring>
#include<queue>
#include<map>
#include<vector>
#include<set>
#include<stack>
#include<cstdio>
#define IOS ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define PII pair<int,int> 
#define inf 0x3f3f3f3f
typedef long long ll;
using namespace std;
string s;
int t,n;
void solve()
{
	cin >> t;
	while(t--){
		cin >> n >> s;
		int ans = 0;
		vector <int> v;  //存放0的位置
		for(int i = 0 ; i < s.size() ; i++){
			if(s[i] == '0') v.push_back(i);
		}
		if(v.size() > 1){
			for(int i = 1 ; i < v.size() ; i++){
				if(v[i] - v[i - 1] > 2) continue; 
				if(v[i] - v[i - 1] == 2) ans++; // 中间差一个1
				if(v[i] - v[i - 1] == 1) ans += 2; //相邻位置的0之间插入两个0
			}
		}
		cout << ans << endl;
	}
}	
int main(){
	IOS;
	solve();
    return 0;
}

B. Marin and Anti-coprime Permutation

 

题意: 一个长度为n的序列,并且每个在【1,n】之间,从第一个位置开始乘以每个位置的下标,

让最终的序列的最大公约数大于1;

思路:既然最大公约数要大于一,那么至少要是二,既然是二,那么必然是偶数,所以我尽可能的让所以数乘以下标变成偶数就可,所以偶数必须大于等于奇数,而假如 n为奇数则不可能,奇数的个数比偶数大一,所以只有n为偶数才有结果,然后奇数对偶数,偶数对奇数,偶数的序列的全排列和奇数的全排列就是答案

AC代码

#include<iostream>
#include<algorithm>
#include<cmath>
#include<deque>
#include<string>
#include<cstring>
#include<queue>
#include<map>
#include<vector>
#include<set>
#include<stack>
#include<cstdio>
#define IOS ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define PII pair<int,int> 
#define inf 0x3f3f3f3f
typedef long long ll;
using namespace std;
const ll mod = 998244353;
ll t,n;
ll N(int x)
{
	ll rs = 1;
	for(int i = 1 ; i <= x ; i++){
		rs *= i;
		rs %= mod;
	}
	return rs;
}
void solve()
{
	cin >> t;
	while(t--){
		cin >> n;
		if(n & 1) cout << 0 << endl;
		else cout << N(n / 2) * N(n / 2) % mod << endl;
	}
}	
int main(){
	IOS;
	solve();
    return 0;
}

C. Shinju and the Lost Permutation

 

 题意:给你一个序列,然后给了你什么叫循环移位,b数组是怎么构成的,bi就是前i个序列的最大值,一个序列的power是里面不同数的个数,题目给了你n个循环移位后序列 的power,问是否存在这样的序列经过n次循环移位得到给出的power值

思路 :核心思考如何不存在,和序列的一些普遍情况,当power为一的时候说明 p1 = n,在这基础上,每进行一次循环移位,应该是power + 1,否则不可能存在这样的序列

AC代码

#include<iostream>
#include<algorithm>
#include<cmath>
#include<deque>
#include<string>
#include<cstring>
#include<queue>
#include<map>
#include<vector>
#include<set>
#include<stack>
#include<cstdio>
#define IOS ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define PII pair<int,int> 
#define inf 0x3f3f3f3f
typedef long long ll;
using namespace std;
int t,n;
void solve()
{
	cin >> t;
	while(t--){
		cin >> n;
		vector <int> v(n);
	//	for(int & x : v) cin >> x;
		for(int i = 0 ; i < v.size() ; i++) cin >> v[i];
		if(count(v.begin(),v.end(),1) != 1){   //查找power为一的个数,多个则不存在
			cout << "NO" << endl;
			continue;
		}
		int pos = find(v.begin(),v.end(),1) - v.begin(); //power = 1的位置
		rotate(v.begin(),v.begin() + pos,v.end()); // 从1的这个位置翻转序列
		int flag = 0;
		for(int i = 1 ; i < v.size() ; i++){
			if(v[i] - v[i - 1] > 1){  // 依次判断
				cout << "NO" << endl;
				flag = 1;
				break;
			}
		}
		if(!flag) cout << "YES" << endl;
	}
}	
int main(){
	IOS;
	solve();
    return 0;
}

D1. 388535 (Easy Version)D1. 388535 (Easy Version)

 

题意: 给你l和r,一个序列为[l,r]的数,给你所有数异或上x的最终序列,问x是多少,x可能是多个,输出任意一个即可

思路:

看一下0 ~ 7的二进制结果

竖着看,每一列的0和1的个数都相等,当这个序列的长度为2^i时都满足这样的 结果,所以当1的个数大于0的个数是,x这一位的二进制一定是1,当0的个数比1的个数大时,x的二进制为一定为0,当0和1 的个数都相等时,0和1都可,最后转换成十进制数就是答案

AC代码 

#include<iostream>
#include<algorithm>
#include<cmath>
#include<deque>
#include<string>
#include<cstring>
#include<queue>
#include<map>
#include<vector>
#include<set>
#include<stack>
#include<cstdio>
#define IOS ios::sync_with_stdio(false),cin.tie(0),cout.tie(0)
#define PII pair<int,int> 
#define inf 0x3f3f3f3f
typedef long long ll;
using namespace std;
int t,n;
int cnt[32][2];
void solve()
{
	cin >> t;
	int l,r,x;
	while(t--){
		memset(cnt,0,sizeof cnt);  //多组样例别忘了
		cin >> l >> r;
	    n = r - l + 1;
		for(int i = l ; i <= r ; i++){
			cin >> x;
			for(int j = 0 ; j <= 30 ; j++,x >>= 1){
				cnt[j][x & 1]++; //当前二进制为0或1出现的次数
			}
		}
		int ans = 0 ;
		for(int i = 0 ; i <= 30 ; i++){
			if(cnt[i][1] >= cnt[i][0]) ans += (1 << i);  //累加上
		}
		cout << ans << endl;
	}
}	
int main(){
	IOS;
	solve();
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值