Codeforces 1491G - Switch and Flip(构造题)
obviously,难度高一点的构造题对我来说都是不可做题
首先考虑将排列拆成一个个置换环,也就是 \(\forall i\) 连边 \(i\to p_i\),显然这样我们可以得到一个个环。
首先考虑怎样同时处理两个置换环,假设有两个环,长度分别为 \(p,q\),元素分别为 \(x_1,x_2,\cdots,x_p;y_1,y_2,\cdots,y_q\)。我们考虑以下步骤同时将这两个环中所有元素复位:
交换 \(x_1,y_1\),两个置换环变为 \(-y_1,x_2,\cdots,x_p;-x_1,y_2,\cdots,y_q\)。
\(\forall i\in[2,q]\),依次交换 \(y_i\) 与原本 \(x_1\) 位置上的数,置换环依次变为:
- \(-y_2,x_2,x_3,\cdots,x_p;-x_1,y_1,y_3,\cdots,y_q\)
- \(-y_3,x_2,x_3,\cdots,x_p;-x_1,y_1,y_2,\cdots,y_q\)
- ……
- \(-y_q,x_2,x_3,\cdots,x_p;-x_1,y_1,y_2,\cdots,y_{q-1}\)
同理 \(\forall i\in[2,p]\) 交换 \(x_i\) 与原本 \(y_1\) 位置上的数,置换环依次变为:
- \(-y_q,x_1,x_3,\cdots,x_p;-x_2,y_1,y_2,\cdots,y_{q-1}\)
- \(-y_q,x_1,x_2,\cdots,x_p;-x_3,y_1,y_2,\cdots,y_{q-1}\)
- ……
- \(-y_q,x_1,x_2,\cdots,x_{p-1};-x_p,y_1,y_2,\cdots,y_{q-1}\)
交换 \(x_p,y_q\)(原本 \(x_1,y_1\) 位置上的数),置换环变为 \(x_p,x_1,x_2,\cdots,x_{p-1};y_q,y_1,y_2,\cdots,y_{q-1}\),大功告成
因此我们实现了用 \(p+q\) 次操作同时处理两个置换环,但是显然置换环的个数不一定是偶数,即可能出现剩余一个置换环的情况,故进一步考虑怎样处理最后一个置换环。
还是假设最后一个置换环的元素分别为 \(x_1,x_2,\cdots,x_p\),分两种情况:
若 \(p\le 2\),我们就找出一个 \(y\) 使得 \(y\) 已经复位了——显然,由于 \(n\ge 2\),我们总能找出这样的 \(y\),那么我们就执行以下操作:
- 交换 \(x_1,y\),当前局面为 \(-y,x_2,-x_1\)
- 交换 \(x_1,x_2\)(原本 \(y,x_2\) 位置上的数),当前局面为 \(-y,x_1,-x_2\)
- 交换 \(x_2,y\)(原本 \(y,x_1\) 位置上的数),当前局面为 \(x_2,x_1,y\)
共使用了三次操作。
若 \(p>2\),那么考虑以下操作:
- \(\forall i\in[2,p-1]\),交换 \(x_i,x_1\) 位置上的数,置换环依次变为:
- \(x_1,x_2,x_3,x_4,\cdots,x_{p-1},x_p\)
- \(-x_2,-x_1,x_3,x_4,\cdots,x_{p-1},x_p\)
- \(-x_3,-x_1,x_2,x_4,\cdots,x_{p-1},x_p\)
- \(-x_4,-x_1,x_2,x_3,\cdots,x_{p-1},x_p\)
- ……
- \(-x_{p-1},-x_1,x_2,x_3,\cdots,x_{p-2},x_p\)
- 此时我们不能再交换 \(x_{p-1}\) 与 \(x_p\) 了,因为那样会使 \(x_1,x_p\) 的操作次数的奇偶性发生错误,因此考虑特判最后三个元素,即执行以下操作:
- 交换 \(x_1,x_p\),得到 \(-x_{p-1},-x_p,x_2,x_3,\cdots,x_{p-2},x_1\)
- 交换 \(x_1,x_{p-1}\),得到 \(-x_1,-x_p,x_2,x_3,\cdots,x_{p-2},x_{p-1}\)
- 交换 \(x_1,x_p\),得到 \(x_p,x_1,x_2,x_3,\cdots,x_{p-2},x_{p-1}\)
共使用了 \(p+1\) 次操作。
- \(\forall i\in[2,p-1]\),交换 \(x_i,x_1\) 位置上的数,置换环依次变为:
这样即可实现本题要求,操作次数不超过 \(n+1\)。
#include <bits/stdc++.h>
using namespace std;
#define fi first
#define se second
#define fill0(a) memset(a,0,sizeof(a))
#define fill1(a) memset(a,-1,sizeof(a))
#define fillbig(a) memset(a,63,sizeof(a))
#define pb push_back
#define ppb pop_back
#define mp make_pair
template<typename T1,typename T2> void chkmin(T1 &x,T2 y){if(x>y) x=y;}
template<typename T1,typename T2> void chkmax(T1 &x,T2 y){if(x<y) x=y;}
typedef pair<int,int> pii;
typedef long long ll;
typedef unsigned int u32;
typedef unsigned long long u64;
namespace fastio{
#define FILE_SIZE 1<<23
char rbuf[FILE_SIZE],*p1=rbuf,*p2=rbuf,wbuf[FILE_SIZE],*p3=wbuf;
inline char getc(){return p1==p2&&(p2=(p1=rbuf)+fread(rbuf,1,FILE_SIZE,stdin),p1==p2)?-1:*p1++;}
inline void putc(char x){(*p3++=x);}
template<typename T> void read(T &x){
x=0;char c=getchar();T neg=0;
while(!isdigit(c)) neg|=!(c^'-'),c=getchar();
while(isdigit(c)) x=(x<<3)+(x<<1)+(c^48),c=getchar();
if(neg) x=(~x)+1;
}
template<typename T> void recursive_print(T x){if(!x) return;recursive_print(x/10);putc(x%10^48);}
template<typename T> void print(T x){if(!x) putc('0');if(x<0) putc('-'),x=~x+1;recursive_print(x);}
void print_final(){fwrite(wbuf,1,p3-wbuf,stdout);}
}
const int MAXN=2e5;
int n,p[MAXN+5],pth_n;
bool vis[MAXN+5];
vector<int> pth[MAXN+5];
int main(){
scanf("%d",&n);
for(int i=1;i<=n;i++) scanf("%d",&p[i]);
for(int i=1;i<=n;i++) if(!vis[i]&&p[i]!=i){
int cur=p[i];pth[++pth_n].pb(i);vis[i]=1;
while(cur!=i) pth[pth_n].pb(cur),vis[cur]=1,cur=p[cur];
} vector<pii> ans;//printf("%d\n",pth_n);
for(int i=1;i+1<=pth_n;i+=2){
ans.pb(mp(pth[i][0],pth[i+1][0]));
for(int j=1;j<pth[i].size();j++) ans.pb(mp(pth[i][j],pth[i+1][0]));
for(int j=1;j<pth[i+1].size();j++) ans.pb(mp(pth[i+1][j],pth[i][0]));
ans.pb(mp(pth[i][0],pth[i+1][0]));
}
if(pth_n&1){
if(pth[pth_n].size()==2){
for(int i=1;i<=n;i++){
if((i^pth[pth_n][0])&&(i^pth[pth_n][1])){
ans.pb(mp(i,pth[pth_n][0]));
ans.pb(mp(i,pth[pth_n][1]));
ans.pb(mp(i,pth[pth_n][0]));
break;
}
}
} else {
for(int i=1;i+1<pth[pth_n].size();i++)
ans.pb(mp(pth[pth_n][0],pth[pth_n][i]));
ans.pb(mp(pth[pth_n][1],pth[pth_n].back()));
ans.pb(mp(pth[pth_n][0],pth[pth_n].back()));
ans.pb(mp(pth[pth_n][0],pth[pth_n][1]));
}
} printf("%d\n",ans.size());
for(int i=0;i<ans.size();i++) printf("%d %d\n",ans[i].fi,ans[i].se);
return 0;
}
Codeforces 1491G - Switch and Flip(构造题)的更多相关文章
- Educational Codeforces Round 7 D. Optimal Number Permutation 构造题
D. Optimal Number Permutation 题目连接: http://www.codeforces.com/contest/622/problem/D Description You ...
- [短期持续更新]Codeforces 构造题一览
说实话我觉得做这种题很没意思(不够硬核), 可是人有短板终究是要补的...起码这种类型补起来相对简单 所以还是把先前准备好的专题放下吧,做点实现上比较休闲的题 ps.为了精简篇幅,代码全部丢到ubun ...
- B - Save the problem! CodeForces - 867B 构造题
B - Save the problem! CodeForces - 867B 这个题目还是很简单的,很明显是一个构造题,但是早训的时候脑子有点糊涂,想到了用1 2 来构造, 但是去算这个数的时候算错 ...
- Codeforces Round #384 (Div. 2) C. Vladik and fractions 构造题
C. Vladik and fractions 题目链接 http://codeforces.com/contest/743/problem/C 题面 Vladik and Chloe decided ...
- Codeforces 482 - Diverse Permutation 构造题
这是一道蛮基础的构造题. - k +(k - 1) -(k - 2) 1 + k , 1 , k , 2, ....... ...
- CodeForces 297C Splitting the Uniqueness (脑补构造题)
题意 Split a unique array into two almost unique arrays. unique arrays指数组各个数均不相同,almost unique arrays指 ...
- codeforces 1438D,思路非常非常巧妙的构造题
大家好,欢迎来到codeforces专题. 今天选择的问题是contest1438的D题,全场通过人数为1325人.一般在codeforces当中千人通过的题难度都不算太高,但是这题有点例外,虽然没有 ...
- Codeforces 1368E - Ski Accidents(构造+思维)
Codeforces 题面传送门 & 洛谷题面传送门 神仙构造题(不过可能我构造太烂了?) 首先考虑这个奇奇怪怪的 \(\dfrac{4}{7}\),以及这个每个点出度最多为 \(2\) 的条 ...
- Codeforces 1270E - Divide Points(构造+奇偶性)
Codeforces 题目传送门 & 洛谷题目传送门 显然,直接暴力枚举是不可能的. 考虑将点按横纵坐标奇偶性分组,记 \(S_{i,j}=\{t|x_t\equiv i\pmod{2},y_ ...
随机推荐
- 【Docker】(11)---Docker的网络概念
一.实现原理 1.实现原理 Docker使用Linux桥接,在宿主机虚拟一个Docker容器网桥(docker0),Docker启动一个容器时会根据Docker网桥的网段分配给容器一个IP地址,称为C ...
- TreeSet和TreeMap中“相等”元素可能并不相等
TreeSet和TreeMap元素之间比较大小是借助Comparator对象的compare方法. 但有些时候,即便compare()返回0也不意味着这两个元素直观上相同. 比如元素是二元组[a,b] ...
- [no code][scrum meeting] Beta 11
$( "#cnblogs_post_body" ).catalog() 例会时间:5月26日11:30,主持者:肖思炀 下次例会时间:5月27日11:30,主持者:乔玺华 一.工作 ...
- UltraSoft - DDL Killer - Alpha 项目展示
团队介绍 CookieLau fmh 王 FUJI LZH DZ Monster PM & 后端 前端 前端 前端 后端 后端 软件介绍 项目简介 项目名称:DDLKiller 项目描述:&q ...
- [对对子队]会议记录4.20(Scrum Meeting11)
今天已完成的工作 何瑞 工作内容:搭建第三关,添加了运行指令标识 相关issue:搭建关卡2.3 相关签入:4.20签入1 4.20签入2 吴昭邦 工作内容:搭建第三关 相关iss ...
- [BUAA]起点 软工第一次作业-热身
项目 内容 这个作业属于哪个课程 2020计算机学院软件工程(罗杰 任健) 这个作业的要求在哪里 第一次作业-热身! 我在这个课程的目标是 了解软件开发,提高自己的工程能力和团队协作能力 这个作业在哪 ...
- OO_JAVA_JML系列第三次作业__架构之谈
OO_JAVA_JML系列第三次作业 ## ----架构之谈 目录 OO_JAVA_JML系列第三次作业 出发点 操作的可分离性 操作本身的多样性 实现手段:表驱动编程 储存 注册 出发点 操作的可分 ...
- js_数据类型转换
转整数----parseInt(string,radix) 1)类似于从左往右匹配数字,直到匹配到非数字结束,并返回匹配到的数字.同parseFloat(). parseInt("123&q ...
- Python爬虫之爬取淘女郎照片示例详解
这篇文章主要介绍了Python爬虫之爬取淘女郎照片示例详解,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧 本篇目标 抓取淘宝MM ...
- 助你上手Vue3全家桶之VueX4教程
目录 1,前言 2,State 2.1,直接使用 2.2,结合computed 3,Getter 3.1,直接使用 3.2,结合computed 4,Mutation 4.1,直接使用 4.2,结合c ...