zoukankan      html  css  js  c++  java
  • UVA

    题目链接

    把一个多边形剖分成若干个三角形,使得其中最大的三角形面积最小。

    比较经典的一道dp问题

    设dp[l][r]为把多边形[l,r]剖分成三角形的最大三角形面积中的最小值,则$dp[l][r]=min{dp[l][i]+dp[i][r]+area(l,i,r)}$

    注意:

    1.由于多边形的点不一定按顺时针或者逆时针排列,需要按点的顺序计算一遍多边形的面积,如果为负说明是顺时针排列,需要反转一下。

    2.进行剖分的时候有可能会“出界”,但无需进行线段相交判断,只需在计算的面积出现负数时返回inf即可。

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 typedef long long ll;
     4 typedef double db;
     5 const int N=50+10;
     6 const db inf=1e18;
     7 struct P {
     8     db x,y;
     9     P operator-(P& b) {return {x-b.x,y-b.y};}
    10 } p[N];
    11 db cross(P a,P b) {return a.x*b.y-a.y*b.x;}
    12 int n;
    13 db calarea() {
    14     db ret=0;
    15     for(int i=1; i<n-1; ++i)ret+=cross(p[i]-p[0],p[i+1]-p[0]);
    16     return ret/2;
    17 }
    18 db calarea(int l,int m,int r) {
    19     return cross(p[l]-p[r],p[m]-p[r])/2;
    20 }
    21 db d[N][N];
    22 db dp(int l,int r) {
    23     if(r-l<2)return 0;
    24     db& ret=d[l][r];
    25     if(ret>=0)return ret;
    26     ret=inf;
    27     for(int i=l+1; i<r; ++i) {
    28         db area=calarea(l,i,r);
    29         if(area>0)ret=min(ret,max(dp(l,i),max(dp(i,r),area)));
    30     }
    31     return ret;
    32 }
    33 
    34 int main() {
    35     int T;
    36     for(scanf("%d",&T); T--;) {
    37         scanf("%d",&n);
    38         for(int i=0; i<n; ++i)scanf("%lf%lf",&p[i].x,&p[i].y);
    39         if(calarea()<0)reverse(p,p+n);
    40         memset(d,200,sizeof d);
    41         printf("%.1f
    ",dp(0,n-1));
    42     }
    43     return 0;
    44 }
  • 相关阅读:
    springBoot 与 springMVC的区别
    spring的IOC和AOP
    实现同步的三种方法
    台阶积水问题
    requsets模块和beautifulsoup模块
    爬虫
    rabbitMQ 消息队列
    Django框架
    mysql
    jQuery
  • 原文地址:https://www.cnblogs.com/asdfsag/p/10451171.html
Copyright © 2011-2022 走看看