contest链接:https://codeforces.com/contest/1269

A. Equation

题意:输入一个整数,找到一个a,一个b,使得a-b=n,切a,b都是合数

思路:合数非常多,从1开始枚举b,a就是b+n,每次check一下a,b是否是合数,是的话直接输出,break即可

AC代码:

 #include<iostream>
#include<string>
#include<vector>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long ll;
ll mod = 1e9+;
const int maxn = 2e5+;
bool check(ll x){
for(int i = ;i<=sqrt(x);i++){
if(x%i == ) return true;
}
return false;
}
int main(){
ll n;cin>>n;
ll cur = ;
while(){
if(check(cur)&&check(cur+n)){
cout<<cur+n<<" "<<cur;
return ;
}
cur++;
}
return ;
}

B. Modulo Equality

题意:有两个序列a,b,要求找到一个相对最小的x,让a序列中的所有元素+x再mod m变为序列b,两个序列内部都可以随意交换

思路:可以发现数据范围很小,直接就可以暴力做。首先对a序列和b序列都进行一下从小到大的排序,首先判一下当前的a序列和b序列是否相等,如果相等直接输出0即可。不相等再进行枚举,以b[1]为基准,枚举a[i]中的每个元素,计算一下b[1]和a[i]模运算差值,让a序列所有的元素加上这个差值之后再判断一下是否和b[i]中的每一个元素相等,取最小的x即可。

AC代码:

#include<iostream>
#include<string>
#include<vector>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long ll;
ll mod = 1e9+;
const int maxn = 2e5+;
int main(){
ll cur = ;
ll n,m;cin>>n>>m;
ll a[],b[];
for(int i = ;i<=n;i++) cin>>a[i];
for(int j = ;j<=n;j++) cin>>b[j];
sort(a+,a+n+);
sort(b+,b+n+);
int f = ;
for(int i = ;i<=n;i++){
if(a[i]!=b[i]) f = ;
}
if(f == ) {
cout<<;
return ;
}
ll ans = 1e9+;
ll c[];
for(int i = ;i<=n;i++){
ll x = b[]>a[i]?b[]-a[i]:b[]+m-a[i];
for(int j = ;j<=n;j++){
c[j] = (a[j]+x)%m;
}
sort(c+,c+n+);
ll f = ;
for(int j = ;j<=n;j++){
if(c[j]!=b[j]) {
f = ;
break;
}
}
if(f == ){
ans = min(ans,x);
}
}
cout<<ans;
return ;
}

C. Long Beautiful Integer

题意:给一个长度为n(长度数据范围2e5)的数字,要求把n转化为大于n且尽可能小的数,使得新的数字每一位 bi = bi+k。

思路:首先对数的前k位进行存储,第k位之后,每一位的数字都受到前k位影响,因为前k位一旦有变换,k位之后必定也需要改变才能满足bi = bi+k,那么只需要对前k位进行枚举即可,每次让前k位组成的数字+1,再变换k位之后的数字,如果这个数字大于最初的n,那么就是break,已经是最小的答案了。同时需要注意一下进位的问题,比如19999,+1之后变为20000,这个也需要处理一下。

AC代码:

    #include<iostream>
#include<string>
#include<vector>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long ll;
ll mod = 1e9+;
const int maxn = 2e5+;
int main(){
ll n,k;cin>>n>>k;
string s;
cin>>s;
string ans = s;
string ak = "";
for(int i = ;i<k;i++){
ak+=s[i];
}
for(int i = k;i<n;i++){
ans[i] = ak[i%k];
}
for(int i = k;i<n;i++){
if(s[i]<ans[i]){
break;
}
if(s[i] == ans[i]){
continue;
}
if(s[i]>ans[i]){
int cur = k - ;
while(ak[cur] == ''){
ak[cur] = '';//处理进位,让所有的9变为0,遇到第一个不是9的让其+1即可
cur--;
}
ak[cur] = ak[cur] + ;
break;
}
}
for(int i = ;i<n;i++){
ans[i] = ak[i%k];
}
cout<<ans.size()<<endl;
cout<<ans;
return ;
}

D. Domino for Young

题意:给一个不规则的网格,在上面放置多米诺骨牌,多米诺骨牌长度要么是1x2,要么是2x1大小,问最多放置多米诺骨牌的数量。

思路:首先这是一个结论题,对每个方格进行染色,一个方格染黑色,周围邻近的就染白色,答案就是黑色方格数量和白色方格数量的最小值。这个结论可以用二分图进行证明:把问题抽象成最大二分图匹配,每两个点之间连一条边。一个格子和周围格子连一条边,如果一个格子周围的还没被匹配,那么匹配数+1。如果一个格子周围已经全部被匹配完,那么该格子可以增广到任意一个为匹配位置,匹配数+1。所以只要在另一种颜色格子数量充沛的情况下,每一次匹配都能对匹配数贡献1,所以答案就是两种颜色的最小值。

AC代码:

#include<iostream>
#include<string>
#include<vector>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long ll;
ll mod = 1e9+;
const int maxn = 2e5+;
int main(){
ll black = , white = ;
int n;cin>>n;
int cur = ;
for(int i = ;i<n;i++){
ll a ;cin>>a;
if(cur == ){
black +=(a/+a%);
white +=a/;
cur = ;
}
else{
cur = ;
black +=a/;
white +=(a/+a%);
}
}
ll ans = min(black,white);
cout<<ans;
return ;
}

E. K Integers

题意:给一个序列P1,P2,P3,P4....Pi,每次可以交换两个相邻的元素,执行最小次数的交换移动,使得最后存在一个子段1,2,…,k,这是题目所定义的f(k),题目要求求出所有的f(n),并依次输出。

思路:首先考虑逆序对问题,比如3 2 1 4这个序列,要使其变为1 2 3 4,最小的移动次数是这个序列中逆序对之和,2+1 = 3,逆序对是(3,2) (3,1)(2,1),但是在比如序列3 5 2 1 6 7 4 8 9,求f(4)怎么做?首先是不是把1 2 3 4这个序列聚成在一起,相连在一起,再去计算逆序对个数,两个过程所花费相加就是答案。那么这个题目就分为两个过程,1.聚合n个数字在一起。2.求逆序对的个数,两者花费相加就行。第1个过程如果使得聚合步数最少呢?其实就是求出聚合后的最中间的位置,其他所有的数字向这个位置靠近所花费的移动次数是最少的,这个过程可以用二分做。第2个过程可以用树状数组,也可以用线段树做。输入的时候记录每个数字的位置,建两个树状数组,一个树状数组维护数字出现的次数,用来求逆序对个数,另一个树状数组维护各个数字在原序列的位置。

 #include<iostream>
#include<string>
#include<vector>
#include<cstring>
#include<cstdio>
#include<algorithm>
#include<cmath>
using namespace std;
typedef long long ll;
ll mod = 1e9+;
const int maxn = 2e5+;
ll t[maxn],cnt[maxn];
ll pos[maxn];
int n;
inline int lowbit(ll x){
return x&(-x);
///算出x二进制的从右往左出现第一个1以及这个1之后的那些0组成数的二进制对应的十进制的数
}
void add(ll *b , int x, int k) {//单点修改
while (x <= n) { //不能越界
b[x] = b[x] + k;
x = x + lowbit(x);
}
}
ll getsum(ll *b,int x) { // a[1]……a[x]的和
ll ans = ;
while (x > ) {
ans = ans + b[x];
x = x - lowbit(x);
}
return ans;
}
int main(){
ios::sync_with_stdio(false);
cin.tie();
cin>>n;
for(int i = ;i<=n;i++){
int t;
cin>>t;
pos[t] = i;//记录t的位置
}
ll inv = ;//记录逆序对的个数
for(int i = ;i<=n;i++){
inv += (i--getsum(t,pos[i]));//每次统计逆序对的个数 ,累加即可
add(t,pos[i],);//在t数组上的pos[i]位置上+1
add(cnt,pos[i],pos[i]);// cnt数组上维护所有数组的位置,
if(i==){
cout<<<<" ";
continue;
}
int mid,l = ,r = n;
while(l<=r){//二分枚举中最中间的位置,所有数字向这个位置靠近
mid = (l+r)>>;
if(getsum(t,mid)*<=i){
l = mid+;
}
else{
r = mid-;
}
}
ll ans = ;
ll cntL = getsum(t,mid);//cntL在mid左边需要的数字个数之和
ll cntR = i - cntL;//cntR是mid右边需要的数字个数之和
ll indexL = getsum(cnt,mid);//mid左边需要数字的位置之和
ll indexR = getsum(cnt,n)-indexL;//mid右边需要数字的位置之和
ans+=((mid+(mid-cntL+))*cntL)/-indexL;//累加mid左边数字靠近邻近mid位置所需要的移动次数
ans+=(indexR-((mid++(mid+cntR))*cntR)/);//累加mid右边数字靠近邻近mid位置所需要的移动次数
cout<<ans+inv<<" ";//逆序对+聚合移动次数为答案
}
return ;
}

Codeforces Round #609 (Div. 2) A-E简要题解的更多相关文章

  1. Codeforces Round #609 (Div. 2)前五题题解

    Codeforces Round #609 (Div. 2)前五题题解 补题补题…… C题写挂了好几个次,最后一题看了好久题解才懂……我太迟钝了…… 然后因为longlong调了半个小时…… A.Eq ...

  2. Codeforces Round #609 (Div. 2) D. Domino for Young

    链接: https://codeforces.com/contest/1269/problem/D 题意: You are given a Young diagram. Given diagram i ...

  3. Codeforces Round #609 (Div. 2) C. Long Beautiful Integer

    链接: https://codeforces.com/contest/1269/problem/C 题意: You are given an integer x of n digits a1,a2,- ...

  4. Codeforces Round #609 (Div. 2)

    A题 给出n,求大于n的两个合数a和b,并且a-b = n 直接输出n的倍数即可 int n; int main() { cin >> n; cout << 9*n <& ...

  5. Codeforces Round #609 (Div. 2) 题解

    Equation Modulo Equality Long Beautiful Integer Domino for Young K Integers Equation \[ Time Limit: ...

  6. Codeforces Round #609 (Div. 2) A到C题

    签到,乘以两个相邻的合数 #include<bits/stdc++.h> using namespace std; int main(int argc, char const *argv[ ...

  7. Codeforces Round #609 (Div. 2) 【A,B,C】

    题意:给一个n<=1e7,找两个合数a和b使得a-b的差为n. 构造a=3n,b=2n,必含有公因子n,只有当n是1的时候是特例. #include<bits/stdc++.h> u ...

  8. Codeforces Round #556 (Div. 2) D. Three Religions 题解 动态规划

    题目链接:http://codeforces.com/contest/1150/problem/D 题目大意: 你有一个参考串 s 和三个装载字符串的容器 vec[0..2] ,然后还有 q 次操作, ...

  9. Codeforces Round #604 (Div. 2) E. Beautiful Mirrors 题解 组合数学

    题目链接:https://codeforces.com/contest/1265/problem/E 题目大意: 有 \(n\) 个步骤,第 \(i\) 个步骤成功的概率是 \(P_i\) ,每一步只 ...

随机推荐

  1. ng-辅助操作

    创建组件,指令,过滤器和服务 # 创建组件 ng generate component my-new-component # 创建组件别名 ng g component my-new-componen ...

  2. JMeter-查找元素

    参考文档:https://jmeter.apache.org/usermanual/hints_and_tips.html 有时很难使用变量或包含某个URL或参数的方法在“测试计划”树和元素中找到. ...

  3. 剑指offer-面试题12-矩阵中的路径-回溯法

    /* 题目: 设计一个函数,判断一个矩阵中是否存在一条包含该字符串所有字符的路径. 路径可从字符串的任意一格开始,每一步可向上.下.左.右移动一格. 如果一条路径经过了矩阵中的某一格,那么该路径不能再 ...

  4. CF895C Square Subsets [线性基]

    线性基的题- 考虑平方数只和拆解质因子的个数的奇偶性有关系 比如说你 \(4\) 和 \(16\) 的贡献都是一样的.因为 \(4 = 2^2 , 16 = 2^4\) \(2\) 和 \(4\) 奇 ...

  5. cin,cin.get(),cin.getline(),gets(),getchar()函数的用法

    1.cin>> 用法a:最基本的流输入用法,接受一个数字或字符,自动跳过输入的空格. 用法b:接受一个字符串,但是遇到除开头外的空格则会终止输入. #include<iostream ...

  6. VS打包程序步骤

    1.下载打包的程序 2.在你的程序里面安装打包的项目 3.添加项目输出 4.为项目添加必要的文件 双击前面建立好的主输出 一般文件为一些配置文件(如使用Nlog写日志,需要添加Nlog的配置文件)和图 ...

  7. 调用window Api 进行对特定窗口的进程ID进行操作

    /// <summary> /// 获取窗口句柄 /// </summary> /// <param name="lpClassName">&l ...

  8. Spark学习之路 (二)Spark2.3 HA集群的分布式安装[转]

    下载Spark安装包 从官网下载 http://spark.apache.org/downloads.html 从微软的镜像站下载 http://mirrors.hust.edu.cn/apache/ ...

  9. 《剑指Offer》各面试题总结

    目录 前言 面试题4 二维数组的查找 面试题5:替换空格 面试题6:从尾到头打印链表 面试题7:重建二叉树 面试题8:二叉树的下一个节点 面试题9:用两个栈实现队列 面试题10:斐波那契数列 面试题1 ...

  10. yii2 环境切换(开发,正式)

    方式一,在web中index修改 开发环境配置 web目录index.php defined('YII_DEBUG') or define('YII_DEBUG', true); defined('Y ...