【牛客网多校】19-7-25-H题 Magic Line
链接:https://ac.nowcoder.com/acm/contest/883/H
来源:牛客网
题目描述
There are always some problems that seem simple but is difficult to solve.ZYB got N distinct points on a two-dimensional plane. He wants to draw a magic line so that the points will be divided into two parts, and the number of points in each part is the same. There is also a restriction: this line can not pass through any of the points.
Help him draw this magic line.
输入描述:
There are multiple cases. The first line of the input contains a single integer T (1≤T≤10000), indicating the number of cases. For each case, the first line of the input contains a single even integer N (2≤N≤1000), the number of points. The following $N$ lines each contains two integers xi,yi (∣xi,yi∣≤1000)It is guaranteed that the sum of N over all cases does not exceed 2×105.输出描述:
For each case, print four integers x1,y1,x2,y2 in a line, representing a line passing through (x1,y1) and (x2,y2). Obviously the output must satisfy (x1,y1)≠(x2,y2). The absolute value of each coordinate must not exceed 109. It is guaranteed that at least one solution exists. If there are multiple solutions, print any of them.
示例1
输入
1 4 0 1 -1 0 1 0 0 -1
输出
-1 999000000 1 -999000001
- 题意
给定平面上一系列的点,求一条以(x1,y1),(x2,y2)两点表示的直线将平面分为包含点数量相等的两部分,其中直线不能穿过任何一点。
- 解题思路
计算几何问题。
示例中的坐标不是随便得到的,将x、y中其中一方拉长到在109以内尽可能大的数,能让直线尽可能水平或者竖直,由于坐标都为整数,这样取值可以使得直线不穿过任何一点,为方便我们取尽可能水平,即x绝对值尽可能大。应该先以y升序,x降序将这些点排序,然后取中位数的两点,若这两点不在同一水平线上,则将这两点的x值扩大;若这两点在同一水平线上,则先将这两点的y坐标一上一下错开,再扩大x的值。
- 错误代码
最开始考虑完整穿过其他点的所有情况,将直线直接取在了中位点上,又为了防止穿过点而将所取点向上下左右错开,直到所取两点不在给出点集合中。但这种情况仅仅是保证了我所取到的点不在点集中,并不能保证他们所连直线是否穿过别的点。
错误代码如下:
1 #include<bits/stdc++.h> 2 using namespace std; 3 typedef long long ll; 4 struct p 5 { 6 ll x,y; 7 }ps[1002]; 8 bool operator <(struct p a,struct p b) 9 { 10 if (a.x!=b.x) return a.x<b.x; 11 else return a.y<b.y; 12 } 13 bool operator ==(struct p a,struct p b) 14 { 15 return a.x==b.x&&a.y==b.y; 16 } 17 bool operator !=(struct p a,struct p b) 18 { 19 return a.x!=b.x||a.y!=b.y; 20 } 21 set <struct p> points; 22 bool cmpx(struct p a,struct p b) 23 { 24 return a.x<b.x; 25 } 26 bool cmpy(struct p a,struct p b) 27 { 28 return a.y<b.y; 29 } 30 int main() 31 { 32 ll t,n; 33 scanf("%lld",&t); 34 while(t--){ 35 ll x1,y1,x2,y2; 36 scanf("%lld",&n); 37 for (ll i=0;i<n;i++){ 38 scanf("%lld %lld",&ps[i].x,&ps[i].y); 39 points.insert(ps[i]); 40 } 41 sort(ps,ps+n,cmpx); 42 x1=ps[n/2-1].x; 43 x2=ps[n/2].x; 44 sort(ps,ps+n,cmpy); 45 y1=ps[n/2-1].y; 46 y2=ps[n/2].y; 47 struct p p1,p2; 48 p1.x=x1;p1.y=y2; 49 p2.x=x2;p2.y=y2; 50 if (p1==p2){ 51 (p1.x)--; 52 (p1.y)--; 53 (p2.x)++; 54 (p2.y)++; 55 } 56 while(points.find(p1)!=points.end()||points.find(p2)!=points.end()){ 57 (p1.x)--; 58 (p2.x)++; 59 } 60 printf("%lld %lld %lld %lld\n",p1.x,p1.y,p2.x,p2.y); 61 } 62 return 0; 63 }
- AC代码
在发现题目的真正做法之后还在另一个地方wa了好多遍,这道题对点的排序也有讲究。先前我们的排序方法是x升序,y升序,但拉长x值的时候是将较大x值向上拉长,较小x值向下拉长。这样选取点的话会造成选取的部分并没有被分开。
即如果我们选择将较大x值向上拉长,较小x值向下拉长的话,这条直线应该是向右上方倾斜的,将平面分成的是左上和右下的两部分,选取点时也自然应该从下到上,从右到左。
AC代码如下:
1 #include<bits/stdc++.h> 2 using namespace std; 3 typedef long long ll; 4 struct p 5 { 6 ll x,y; 7 }ps[1002]; 8 bool cmpx(struct p a,struct p b) 9 { 10 return a.x<b.x; 11 } 12 bool cmpy(struct p a,struct p b) 13 { 14 if(a.y!=b.y) return a.y<b.y; 15 else return a.x>b.x; 16 } 17 int main() 18 { 19 ll t,n; 20 scanf("%lld",&t); 21 while(t--){ 22 ll x1,y1,x2,y2; 23 scanf("%lld",&n); 24 for (ll i=0;i<n;i++){ 25 scanf("%lld %lld",&ps[i].x,&ps[i].y); 26 } 27 sort(ps,ps+n,cmpy); 28 x1=(ps[n/2-1].x); 29 y1=ps[n/2-1].y; 30 x2=(ps[n/2].x); 31 y2=ps[n/2].y; 32 x1-=999000000; 33 x2+=999000000; 34 if (y1==y2) { 35 y1-=1; 36 y2+=1; 37 } 38 printf("%lld %lld %lld %lld\n",x1,y1,x2,y2); 39 } 40 return 0; 41 }
转载于:https://www.cnblogs.com/sixwater6H2O/p/11247568.html
【牛客网多校】19-7-25-H题 Magic Line相关推荐
- [题解] 2019牛客暑期多校第三场H题 Magic Line
题目链接:https://ac.nowcoder.com/acm/contest/883/H 题意:二维平面上有n个不同的点,构造一条直线把平面分成两个点数相同的部分. 题解:对这n个点以x为第一关键 ...
- 牛客网剑指offer编程实践1-10题
牛客网剑指offer编程实践1-10题 1.二维数组中的查找 在一个二维数组中(每个一维数组的长度相同),每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序.请完成一个函数,输入这 ...
- 2021牛客暑假多校第八场 K题—Yet Another Problem About Pi
2021牛客暑假多校第八场 K题-Yet Another Problem About Pi 题意:告诉你一个单元格的长和宽,问你走Π(3.1415926-)的长度距离最多可以走几个单元格 思路:沿着单 ...
- 2021牛客暑期多校训练营2,签到题CDFKI
2021牛客暑期多校训练营2 题号 标题 已通过代码 通过率 团队的状态 A Arithmetic Progression 点击查看 6/72 未通过 B Cannon 点击查看 34/104 未通过 ...
- “蔚来杯“2022牛客暑期多校训练营10,签到题HFIE
题号 标题 已通过代码 通过率 团队的状态 A Everlasting Transeunt 点击查看 6/42 B Fall Guys-Perfect Match 点击查看 6/115 C Magic ...
- 牛客网剑指offer编程实践41-50题
41.和为S的连续正数序列 小明很喜欢数学,有一天他在做数学作业时,要求计算出9~16的和,他马上就写出了正确答案是100.但是他并不满足于此,他在想究竟有多少种连续的正数序列的和为100(至少包括两 ...
- 牛客网_PAT乙级_1010月饼 (25)
因为黑框框里放不下,(非官网)测试用例用txt导入: 这题有一个陷阱,官网上说给非0数,测试用例却出现了0,0吨的月饼能卖507元,而且这样的月饼要最先卖,因为它的price是inf,卖掉0吨净赚50 ...
- 牛客网多校第4场 D Another Distinct Values 【构造】
题目:戳这里 题意,n*n的矩阵,只能填-1,0,1,问能不能使该矩阵的任意行和列的和都不想等. 解题思路:戳这里 可以说是一目了然了 附ac代码: 1 #include<iostream> ...
- 牛客网多校第9场 E Music Game 【思维+数学期望】
题目:戳这里 题意:鼠标点击n下,第i次点击成功的概率为p[i],连续点击成功x次可以获得x^m分,求n次点击总分数的数学期望. 解题思路:数学期望的题很多都需要转化思维,求某一个单独状态对整体答案的 ...
最新文章
- 深入理解Java中的final关键字
- 安装SQL2K,当创建挂起文件操作之后...
- 看动画学算法系列之:后缀数组suffix array
- gcc 5.2.0 手动更新(亲测)
- 分数相同名次排名规则C语言,如何给数据排名(相同分数相同名次)-excel篇
- try-catch的使用以及细节
- LaTex ——P4 字体字号设置
- 健康E生 十八种食品点亮你健康生命
- telnet发送socket报文_简单讲解一下Socket网络编程
- 【机器学习系列】EM算法第一讲:EM算法相关概述及收敛性证明
- 软考高项-了解软考高项
- qtcreator编译qt程序是如何调用moc的,如何通过pro文件向moc传入参数
- Android app跳转QQ加人聊天或者加群
- 软件测试-柠檬班python全栈自动化50期测试学习笔记分享
- python文本保存
- Appium环境搭建和检测
- char与varchar详解
- saber框架 blade-core-tool:2.5.1 maven无法正常下载
- Mac 环境下 Java JDK 的安装与环境变量配置详解(已完美解决)
- HarmonyOS系统架构