3301 Texas Trip 解题报告
首次领教了三分法,对于二分、三分解决一些数学问题有了更加深刻的领悟。
题意:求最小面积的正方形,覆盖平面上给定的N个点。
算法:三分逐步细分。标准正放正方形的比较好做只要找出minx,miny,maxx,maxy即可但是最小正方形不一定是标准正放,每个点对角度坐标表换的值,( x = node[j].x * cos(angle) - node[j].y * sin(angle);y = node[j].y * cos(angle) + node[j].x * sin(angle);)然后求标准正放的最小正方形即可。
AC代码:
#include <math.h>
#include <stdio.h>
#define MAX 1000000000
#define MIN -1000000000
#define pi (asin(1.)*2)
struct Texas
{
int x, y;
};
int main()
{
freopen("1.txt", "r", stdin);
int i, j, test, n;
scanf("%d", &test);
while (test--)
{
Texas node[31];
scanf("%d", &n);
for (i = 0; i < n; i++)
{
scanf("%ld%ld", &node[i].x, &node[i].y);
}
int times = 40;
double cumulative = pi / 6, angle = 0, minboundary = MAX, from = 0, boundary;
double downx, downy, upx, upy, x, y;
while (times--)
{
for (i = 0; i < 4; i++) //角度初始为0,那么4次相加后,将超过90
{
downx = downy = MAX; upx = upy = MIN;
for (j = 0; j < n; j++)
{
x = node[j].x * cos(angle) - node[j].y * sin(angle);
y = node[j].y * cos(angle) + node[j].x * sin(angle);
if (x < downx) downx = x;
if (x > upx) upx = x;
if (y < downy) downy = y;
if (y > upy) upy = y;
}
boundary = (upx - downx) > (upy - downy) ? (upx - downx) : (upy - downy);
if (boundary < minboundary)
{
minboundary = boundary;
from = angle;
}
angle += cumulative;
}
//逐步细分
if (angle)
{
angle = from - cumulative;
}
//三分思想的应用
if (angle == 0 || angle == 3)
{
cumulative /= 3;
}
else
{
cumulative = cumulative * 2 / 3;
}
}
printf("%.2lf/n", minboundary * minboundary);
}
return 0;
}