大致思路:
每一行的点和每一列的点都连上边,然后用dfs的方法把图变为一颗搜索树,然后由叶子向根删除节点即可
#include<iostream>
#include<cstring>
#include<cstdio>
#include<queue>
using namespace std;
const int nMax = 2010;
const int mMax = 3000008;
class edge{
public:
int v,nex;
};edge e[mMax];
int k,head[nMax];
void addedge(int a,int b){
e[k].v=b;
e[k].nex=head[a];
head[a]=k;k++;
}
class pxx{
public:
int x,y;
}pos[nMax];
int n,m,vis[nMax],ope[nMax][3],cnt;
void dfs(int loc){
vis[loc]=1;
for(int i=head[loc];i;i=e[i].nex){
int v=e[i].v;
if(vis[v])continue;
dfs(v);
if(pos[v].x==pos[loc].x){
if(pos[v].y>pos[loc].y){
ope[cnt][0]=1;
ope[cnt][1]=v;
cnt++;
}else{
ope[cnt][0]=2;
ope[cnt][1]=v;
cnt++;
}
}else{
if(pos[v].x>pos[loc].x){
ope[cnt][0]=3;
ope[cnt][1]=v;
cnt++;
}else{
ope[cnt][0]=4;
ope[cnt][1]=v;
cnt++;
}
}
}
}
int main(){
int i,j;
while(scanf("%d",&n)!=EOF){
for(i=1;i<=n;i++){
scanf("%d%d",&pos[i].x,&pos[i].y);
}
k=1;
memset(head,0,sizeof(head));
for(i=1;i<=n;i++){
for(j=i+1;j<=n;j++){
if(pos[i].x==pos[j].x||pos[i].y==pos[j].y){
addedge(i,j);
addedge(j,i);
}
}
}
int res=0;
cnt=0;
memset(vis,0,sizeof(vis));
for(i=1;i<=n;i++){
if(vis[i])continue;
res++;
dfs(i);
}
printf("%d\n",res);
for(i=0;i<cnt;i++){
printf("(%d, %d) ",pos[ope[i][1]].x,pos[ope[i][1]].y);
if(ope[i][0]==1)printf("DOWN\n");
else if(ope[i][0]==2)printf("UP\n");
else if(ope[i][0]==3)printf("LEFT\n");
else if(ope[i][0]==4)printf("RIGHT\n");
}
}
return 0;
}