题解:AT_arc207_b [ARC207B] Balanced Neighbors 2
题意
构造一个无向图
其中,
思路
分类讨论奇数和偶数。
-
偶数
先以
n=6 举例。考虑构造出一个完全图:
令
发现
把点
考虑构造一个二分图,
之后对每个左部点和右部点连边(对应点除外):
构造后发现,每个左部点都可以用一步到达所有右部点(对应点除外),右部点同理。所以每个点
此时
-
奇数
在偶数的基础上拓展。
以
n=7 为例。
点
综上:偶数时将左部点连向所有不对应的右部点,奇数时多出的一个点向一侧的所有点连边即可。
时间复杂度:
代码
#include<bits/stdc++.h>
#define int long long
#define bug cout<<"___songge888___"<<'\n';
using namespace std;
int n;
vector<pair<int,int> >ans;
signed main(){
ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
cin>>n;
if(n<=5){
cout<<-1;
}
else if(n%2==0){
for(int i=1;i<=n/2;i++){
for(int j=1;j<=n/2;j++){
int x=i*2-1;
int y=j*2;
if(x+y==n+1){
continue;
}
ans.push_back({x,y});
// cout<<x<<' '<<y<<'\n';
}
}
cout<<ans.size()<<'\n';
for(auto [x,y]:ans){
cout<<x<<' '<<y<<'\n';
}
}
else{
n--;
for(int i=1;i<=n/2;i++){
for(int j=1;j<=n/2;j++){
int x=i*2-1;
int y=j*2;
if(x+y==n+1){
continue;
}
ans.push_back({x,y});
// cout<<x<<' '<<y<<'\n';
}
}
for(int i=1;i<=n/2;i++){
ans.push_back({i*2-1,n+1});
// cout<<i<<' '<<n+1<<'\n';
}
cout<<ans.size()<<'\n';
for(auto [x,y]:ans){
cout<<x<<' '<<y<<'\n';
}
}
return 0;
}