博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Luogu4423 BJWC2011 最小三角形 平面最近点对
阅读量:5062 次
发布时间:2019-06-12

本文共 2388 字,大约阅读时间需要 7 分钟。

题意:给出$N$个点,求其中周长最小的三角形(共线的也计算在内)。$N \leq 2 \times 10^5$


这道题唤起了我对平面最近点对的依稀记忆

考虑平面最近点对的分治,将分界线两边的求解改为求三角形的最小边长即可。

小心坐标乘积爆int

不难但就是想不出

1 //This code is written by Itst 2 #include
3 #define int long long 4 #define ld long double 5 #define eps (ld)1e-10 6 using namespace std; 7 8 inline int read(){ 9 int a = 0;10 bool f = 0;11 char c = getchar();12 while(c != EOF && !isdigit(c)){13 if(c == '-')14 f = 1;15 c = getchar();16 }17 while(c != EOF && isdigit(c)){18 a = (a << 3) + (a << 1) + (c ^ '0');19 c = getchar();20 }21 return f ? -a : a;22 }23 24 const int MAXN = 200010;25 struct node{26 int x , y;27 }now[MAXN] , pot[MAXN];28 int N;29 30 ld dis(node a , node b){31 return sqrt((a.x - b.x) * (a.x - b.x) + (a.y - b.y) * (a.y - b.y));32 }33 34 ld len(node a , node b , node c){35 return dis(a , b) + dis(b , c) + dis(a , c);36 }37 38 bool cmp1(node a , node b){39 return a.y < b.y;40 }41 42 ld solve(int l , int r){43 if(r - l <= 4){44 ld minN = 0x3f3f3f3f;45 for(int i = l ; i <= r ; i++)46 for(int j = i + 1 ; j <= r ; j++)47 for(int k = j + 1 ; k <= r ; k++)48 minN = min(minN , len(now[i] , now[j] , now[k]));49 return minN;50 }51 int mid = l + r >> 1;52 ld k = (now[mid].x + now[mid + 1].x) * (ld)0.5 , d1 = solve(l , mid) , d2 = solve(mid + 1 , r) , d = min(d1 , d2);53 sort(now + l , now + r + 1 , cmp1);54 int p = 0;55 for(int i = l ; i <= r ; i++)56 if(fabs(now[i].x - k) + eps < d)57 pot[++p] = now[i];58 for(int i = 1 ; i <= p ; i++)59 for(int j = i + 1 ; j <= p && pot[j].y - pot[i].y + eps < d ; j++)60 for(int k = j + 1 ; k <= p && pot[k].y - pot[i].y + eps < d ; k++)61 d = min(d , len(pot[i] , pot[j] , pot[k]));62 return d;63 }64 65 bool cmp(node a , node b){66 return a.x < b.x;67 }68 69 signed main(){70 #ifdef LG71 freopen("4423.in" , "r" , stdin);72 //freopen("4423.out" , "w" , stdout);73 #endif74 N = read();75 for(int i = 1 ; i <= N ; i++){76 now[i].x = read();77 now[i].y = read();78 }79 sort(now + 1 , now + N + 1 , cmp);80 cout << fixed << setprecision(6) << solve(1 , N);81 return 0;82 }

转载于:https://www.cnblogs.com/Itst/p/9879394.html

你可能感兴趣的文章
控制复选框的全选或反选
查看>>
utf8和unicode
查看>>
PHP导入导出csv文件 Summer-CSV
查看>>
UWP 双向绑定,在ListView中有个TextBox,怎么获取Text的值
查看>>
OpenGL学习-------visual studio 2010配置和第一个OpenGL程序讲解
查看>>
python入门-分类和回归各种初级算法
查看>>
Day4 Python基础之数据类型(三)
查看>>
http状态码
查看>>
执行计划--在存储过程中使用SET对执行计划的影响
查看>>
『科学计算』L0、L1与L2范数_理解
查看>>
有十二个球,大小形状相同。其中一个重量与其他十一个不同,现在要求用一没有砝码的天平称三次找出那个球,并确定特殊球是轻还是重...
查看>>
React学习之State
查看>>
<link rel="icon" href="images/favicon.ico.png" /> 插入网站最上面标题旁的图标
查看>>
mysql binlog配置详解
查看>>
python 下载整个站点
查看>>
三个摘要
查看>>
Java 测试并行编程(三)
查看>>
history for html5
查看>>
Java并发:volatile内存可见性和指令重排
查看>>
java学习面向对象之接口
查看>>