传送门UVa 10112 - Myacm Triangles
总算让我做出一题了.
题目前面都在扯蛋, 我还看了半天
题意是给出几个点, 让我们找出一个面积最大且内部(包括边界)没有点的三角形.
想不出更好的办法, 只好枚举了.
我的思路是先计算面积是否大于当前的最大面积, 如果是, 再判断他的内部有没有点. 如果没有, 记录顶点.
注意计算面积的时候要取绝对值,被这里坑了一次
判断一个点是否在一个三角形中, 我采用的是叉乘法.
详情请点这里.
详情见代码
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <cmath>
using namespace std;
struct point
{
char name;
int x, y;
};
double CalcuS(int i, int j, int k);
bool Judge(int x, int i, int j, int k);
void Record(int i, int j, int k);
int comp(const void *_a, const void *_b)
{
char *a = (char *)_a;
char *b = (char *)_b;
return *a - *b;
}
point dian[50];
char temp[10];
int main()
{
//freopen("input.txt", "r", stdin);
int n;
int i, j, k, l;
double S, Smax;
while (scanf("%d", &n))
{
memset(temp, 0, sizeof(temp));
memset(dian, 0, sizeof(dian));
getchar();
if (n == 0)
break;
for (i = 0; i < n; i++)
{
scanf("%c%d%d", &dian[i].name, &dian[i].x, &dian[i].y);
getchar();
}
Smax = -1;
for (i = 0; i < n; i++)
{
for (j = i + 1; j < n; j++)
{
for (k = j + 1; k < n; k++)
{
S = CalcuS(i, j, k);
if (S <= Smax || S == 0)
continue;
else
{
for (l = 0; l < n; l++) //扫描除了三点以外的所有的点
{
if (l == i || l == j || l == k) //如果是现在的点就跳过.
continue;
if (Judge(l, i, j, k) == true) //如果有点在这三点里面, 不符合要求.
break;
}
if (l == n) //符合要求的, 记录字母, 和最大面积
{
Smax = S;
Record(i, j, k);
}
}
}
}
}
qsort(temp, 3, sizeof(temp[0]), comp); //排序
printf("%s\n", temp);
}
return 0;
}
void Record(int i, int j, int k)
{
temp[0] = dian[i].name;
temp[1] = dian[j].name;
temp[2] = dian[k].name;
}
double CalcuS(int i, int j, int k)
{
return 0.5 * fabs(((dian[k].y - dian[i].y) * (dian[j].x - dian[i].x) - (dian[j].y - dian[i].y) * (dian[k].x - dian[i].x)));
}
bool Judge(int M, int i, int j, int k)
{
int a, b, c;
int x = dian[M].x;
int y = dian[M].y;
point MA, MB, MC;
MA.x = dian[i].x - x;
MA.y = dian[i].y - y;
MB.x = dian[j].x - x;
MB.y = dian[j].y - y;
MC.x = dian[k].x - x;
MC.y = dian[k].y - y;
a = MA.x * MB.y - MB.x * MA.y;
b = MB.x * MC.y - MC.x * MB.y;
c = MC.x * MA.y - MA.x * MC.y;
if (a >= 0 && b >= 0 && c >= 0 || a <= 0 && b <= 0 && c <= 0)
return true;
else
return false;
}