Description
Input
Output
Sample Input
14-1.00 0.000.00 -3.002.00 2.002.00 0.00
Sample Output
2.00
题目大意:
john 要在一片森林里放牛,但是 john 怕牛到处乱跑,而他有比较懒,所以他想找几棵树围起来,这要他就可以吃着小菜、喝着小酒在旁边悠哉了,现在他想让你帮他算出围城的圈中最小的面积是多少。
输入:
输入 t 表示有t组测试数据
输入 n ,表示该组数据中有 n 棵树
接下来 n 行分别输入 n 课数的坐标点
输出:
输出能围成的最小面积,但不能为 0
思路分析:
要围成的面积最小,那么肯定就是选三棵树了,小于三棵树的围不成,大于三棵的围成的面积肯定比三棵的面积大,所以就算三棵树围就行了,因此,该题到这就有两种方式求, 一种是 : 一言不合就搜索 (⊙o⊙)… 从 n 棵树种搜三棵树,围成的面积,取最小的。另一种就是:随随便便就暴力 (*@ο@*) ~ ,直接三个for 循环,暴力求解,记录下来最小值。
不过在这道题中还有个坑的地方,精度问题 23333333333333,如果你只先根据点求出每条边的长度,然后再根据海伦公式求面积,那么恭喜你,你将面临的是 WA,我就因为这wa了无数次 ,顿时一脸懵逼O__O "…..... ,最后想想,应该是精度问题,可能中间计算出现精度损失了。
好了,说了这么多废话,说说这道题用的公式吧,这道题用的是 由三点坐标直接求三角形面积的公式。
设三角形的三个顶点坐标为 A( x1 , y1 ) B( x2 , y 2 ) C ( x3 , y3 )
则 三角形的 面积 S = ( x2 - x1 ) * ( y3 - y1) - ( y2 - y1 ) * ( x3 - x1 )
证明过程我就不写了,大家可以自己回去推导证明一下
附上代码:(搜索)
#include<stdio.h>
#include<math.h>
#include<string.h>
#define min(x,y) x > y ? y : x
double x[5],y[5],xx[300],yy[300],area;
void dfs(int n,int t)
{
if(t == 4)
{
double area1 = (fabs((x[2]-x[1])*(y[3] - y[1]) - (y[2]-y[1])*(x[3]-x[1])))/2;
if(area1 == 0)
return;
area = min(area1,area);
return ;
}
int i;
for(i = n;i >= 0;i--)
{
x[t] = xx[i];
y[t] = yy[i];
dfs(i-1,t+1);
}
}
int main()
{
int k;
scanf("%d",&k);
while(k--)
{
memset(x,0,sizeof(x));
memset(xx,0,sizeof(xx));
memset(y,0,sizeof(y));
memset(yy,0,sizeof(yy));
area = 99999;
int l;
scanf("%d",&l);
int i;
for(i = 0;i < l;i++)
{
scanf("%lf%lf",&xx[i],&yy[i]);
}
dfs(l-1,1);
if(area == 99999)
printf("Impossible\n");
else
printf("%.2lf\n",area);
}
return 0;
}