凸包的答辩日记

该文章描述了一段C++代码,用于处理点的排序和根据特定规则检测冲突。程序使用了自定义排序规则,基于点的相对位置和距离,并利用堆栈进行出栈操作来处理特殊情况。在处理过程中,作者发现了代码中关于映射和冲突检测的错误。
摘要由CSDN通过智能技术生成

想了很久的der 被自己蠢到了好久

1.数组散列映射关系看眼花了   多映射一层

  bool sortRule()里映射错误,明明i,j就是index[]的值还再次映射

2.大脑里没有考虑到点排布特殊情况,出栈操作的while是没有想到的。只考虑与前一点冲突,没有考虑与记载的拟前驱节点群冲突。

#include<iostream>
#include<cmath>
#include<algorithm>
#include<iomanip>
#define epis 1E-8
using namespace std;

typedef struct{
	long double x;
	long double y;
}Point;
 
Point point[10010];
int index[10010];
int stack[10010];

int isDir(Point t0,Point t1,Point t2){
	long double sum;
	sum=t0.x*(t1.y-t2.y)+t1.x*(t2.y-t0.y)+t2.x*(t0.y-t1.y);
	if(sum>epis) return 1;
	else if(sum<-epis) return -1;
	else return 0;
}
long double Dis_sq(Point t0,Point t1){
	return sqrt((t0.x-t1.x)*(t0.x-t1.x)+(t0.y-t1.y)*(t0.y-t1.y));
}
bool sortRule(int i,int j){
	int dir;
	dir=isDir(point[index[0]],point[i],point[j]);
	if(dir==-1) return false;
	else if(dir==1) return true;
	else if(dir==0){
		long double dis1,dis2;
		dis1=sqrt(Dis_sq(point[index[0]],point[i]));
		dis2=sqrt(Dis_sq(point[index[0]],point[j]));
		if(dis1-dis2<-epis) return true;
		else if(dis1-dis2>epis) return false;
	}
}
int main(){
	int k,n,i,top;
	long double max_,max;
	max=0.0;
	cin>>n;
	for(i=0;i<n;i++){
		cin>>point[i].x>>point[i].y;
		index[i]=i;
	}
	for(i=1,k=0;i<n;i++){
		if(point[k].y-point[i].y>epis) k=i;
		else if(point[k].y-point[i].y<-epis);
		else if(point[k].x-point[i].x>epis) k=i;
	}
	index[0]=k,index[k]=0;
	sort(index+1,index+n,sortRule);
	top=1;
	stack[top]=index[0],stack[++top]=index[1];
	for(i=2;i<n;i++){
		while(top>1&&isDir(point[stack[top-1]],point[stack[top]],point[index[i]])<=0) top--;
		stack[++top]=index[i];
	}
	for(i=1;i<top;i++){
		for(k=i+1;k<=top;k++){
			max_=Dis_sq(point[stack[i]],point[stack[k]]);
			if(max_-max>epis) max=max_;
		} 
	}
	cout<<setiosflags(ios::fixed)<<setprecision(4)<<max<<endl;
	for(i=1;i<top;i++) cout<<stack[i]<<" ";
	cout<<stack[i];
	return 0;
}

总结:堆栈太神奇了,看麻了 小看它了

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值