• P1378 油滴扩展 dfs回溯法


      

    题目描述

    在一个长方形框子里,最多有N(0≤N≤6)个相异的点,在其中任何一个点上放一个很小的油滴,那么这个油滴会一直扩展,直到接触到其他油滴或者框子的边界。必须等一个油滴扩展完毕才能放置下一个油滴。那么应该按照怎样的顺序在这N个点上放置油滴,才能使放置完毕后所有油滴占据的总体积最大呢?(不同的油滴不会相互融合)

    注:圆的面积公式V=pi*r*r,其中r为圆的半径。

    输入输出格式

    输入格式:

    第1行一个整数N。

    第2行为长方形边框一个顶点及其对角顶点的坐标,x,y,x’,y’。

    接下去N行,每行两个整数xi,yi,表示盒子的N个点的坐标。

    以上所有的数据都在[-1000,1000]内。

    输出格式:

    一行,一个整数,长方形盒子剩余的最小空间(结果四舍五入输出)

    输入输出样例

    输入样例#1: 复制
    2
    20 0 10 10
    13 3
    17 7
    
    输出样例#1: 复制
    50


    6个点 回溯法即可 也不用剪枝

    注意一一些特殊情况 比如半径不可能为负数

    #include<bits/stdc++.h>
    using namespace std;
    //input by bxd
    #define rep(i,a,b) for(int i=(a);i<=(b);i++)
    #define repp(i,a,b) for(int i=(a);i>=(b);--i)
    #define RI(n) scanf("%d",&(n))
    #define RII(n,m) scanf("%d%d",&n,&m)
    #define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
    #define RS(s) scanf("%s",s);
    #define ll long long
    #define REP(i,N)  for(int i=0;i<(N);i++)
    #define CLR(A,v)  memset(A,v,sizeof A)
    //////////////////////////////////
    #define inf 0x3f3f3f3f
    #define N 2000+5
    #define PI 3.1415926
    int n,m;
    double X,Y;
    struct node
    {
        double x,y;
    }s[10];
    int vis[N];
    double maxx;
    double R[10];
    double getr(int x)
    {
        double ans=min( min( s[x].x,X-s[x].x), min( s[x].y,Y-s[x].y )  );
        rep(i,1,n)
        if(x!=i)
        {
            if(R[i]==0)continue;
            double d=sqrt( (s[x].x-s[i].x)*(s[x].x-s[i].x)+ (s[x].y-s[i].y)*(s[x].y-s[i].y) )-R[i];
            ans=min(ans,d);
        }
        if(ans>0)
        return ans;
        return 0;
    }
    void dfs(int cnt,double sum)
    {
        if(cnt==n+1)
        {
            maxx=max(maxx,sum);
            return ;
        }
    
        rep(i,1,n)
        if(!vis[i])
        {
            double temp=getr(i);
            vis[i]=1;
            R[i]=temp;
            dfs(cnt+1,sum+temp*PI*temp);
            R[i]=0;
            vis[i]=0;
        }
    }
    
    int main()
    {
       RI(n);
       int a,b,c,d;
       RII(a,b);RII(c,d);
       int x1=min(a,c);
       int y1=min(b,d);
       Y=abs(b-d),X=abs(a-c);
       rep(i,1,n)
       {
           int q,w;
           RII(q,w);
           q-=x1;
           w-=y1;
           s[i].x=(double)q;
           s[i].y=(double)w;
       }
       maxx=0;
       dfs(1,0);
       printf("%d",(int)(X*Y-maxx+0.5) );
       return 0;
    }
    View Code



  • 相关阅读:
    java中float和double的区别
    常用的排序算法及其适用场景
    高级排序
    LoadRunner 学习笔记(1)性能测试常见术语
    Oracle 常用函数
    oracle 自定义函数
    Oracle 异常处理
    Oracle 包(package)
    CF1332B Composite Coloring(数学)
    CF55D Beautiful(数位dp)
  • 原文地址:https://www.cnblogs.com/bxd123/p/10725686.html
Copyright © 2020-2023  润新知