zoukankan      html  css  js  c++  java
  • POJ

    题目大意:给出一条圆弧上的两个端点A,B,和圆弧上两端点之间的一个点C,现在要用一块各个定点的坐标均为整数的矩形去覆盖这个圆弧,要求最小的矩形面积。

    思路:叉积在本体发挥很强大的作用。首先求出三个点所在圆的圆心,也就是三角形的外心,然后判断着个圆上最上,最下,最左,最右四个点是否在该圆弧上,如果在,那么所求矩形的最上,最下,最左,最右边的坐标就是对应的点的坐标,否则,应该有圆弧两端点的坐标的相对大小来确定!
    要判断一个点是否在圆弧上,主要用到叉积!把AB连结起来,设待检测的点式P,则如果是p在圆弧上,那么点p和点C在直线AB 的同一侧,否则在异侧,所以可由叉积判断!
    #include <iostream>
    #include<cstdio>
    #include<cstring>
    #include<algorithm>
    #include<stdlib.h>
    #include<vector>
    #include<cmath>
    #include<queue>
    #include<set>
      using namespace std;
      #define N 100000
      #define LL long long
      #define INF 0xfffffff
      const double eps = 1e-8;
      const double pi = acos(-1.0);
     const double inf = ~0u>>2;
      struct Point
     {
          double x,y;
          Point(double x=0,double y=0):x(x),y(y) {}
      }p[4];
      typedef Point pointt;
      pointt operator + (Point a,Point b)
      {
           return Point(a.x+b.x,a.y+b.y);
      }
      pointt operator - (Point a,Point b)
      {
             return Point(a.x-b.x,a.y-b.y);
      }
      int dcmp(double x)
      {
          if(fabs(x)<eps) return 0;
          else return x<0?-1:1;
      }
      struct Circle
      {
          Point center;
          double r;
      };
      double cross(Point a,Point b)
      {
          return a.x*b.y-a.y*b.x;
      }
      double mul(Point p0,Point p1,Point p2)
      {
          return cross(p1-p0,p2-p0);
      }
      double dis(Point a)
      {
          return a.x*a.x+a.y*a.y;
     }
      double area()
     {
          return fabs(cross(p[1]-p[3],p[2]-p[3]))/2;
      }
      bool seginter(pointt a1,pointt a2,pointt b1,pointt b2)
      {
           double c1 = cross(a2-a1,b1-a1),c2 = cross(a2-a1,b2-a1),
                  c3 = cross(b2-b1,a1-b1),c4 = cross(b2-b1,a2-b1);
           return dcmp(c1)*dcmp(c2)<0&&dcmp(c3)*dcmp(c4)<0;
      }
      struct Circle Circumcircle()
     {
          Circle tmp;
          double a,b,c,c1,c2;
         double xa,ya,xb,yb,xc,yc;
          a = sqrt(dis(p[3]-p[1]));
          b = sqrt(dis(p[1]-p[2]));
          c = sqrt(dis(p[2]-p[3]));
         tmp.r = (a*b*c)/(area()*4.0);
          xa = p[3].x;
          ya = p[3].y;
          xb = p[1].x;
          yb = p[1].y;
         xc = p[2].x;
          yc = p[2].y;
          c1 = (dis(p[3])-dis(p[1]))/2;
          c2 = (dis(p[3])-dis(p[2]))/2;
          tmp.center.x = (c1*(ya-yc)-c2*(ya-yb))/((xa-xb)*(ya-yc)-(xa-xc)*(ya-yb));
         tmp.center.y = (c1*(xa-xc)-c2*(xa-xb))/((ya-yb)*(xa-xc)-(ya-yc)*(xa-xb));
          return tmp;
      }
      int main()
      {
         int i;
          double r;
          int w0,w1,h0,h1;
          for(i = 1; i <= 3 ; i++)
          scanf("%lf%lf",&p[i].x,&p[i].y);
          Circle cc = Circumcircle();
          r = cc.r;
    
          Point q[5];
          for(i = 1 ;i < 5 ;i++)
         q[i] = cc.center;
          q[1].x-=r,q[2].x+=r,q[3].y-=r,q[4].y+=r;
    
        if(!seginter(q[1],p[3],p[1],p[2])) w0 = floor(q[1].x+eps);
         else w0 = floor(min(p[1].x,p[2].x)+eps);
    
         if(!seginter(q[2],p[3],p[1],p[2]))  w1 = ceil(q[2].x-eps);
        else w1 = ceil(max(p[1].x,p[2].x)-eps);
    
         if(!seginter(q[3],p[3],p[1],p[2])) h0 = floor(q[3].y+eps);
         else h0 = floor(min(p[1].y,p[2].y)+eps);
    
         if(!seginter(q[4],p[3],p[1],p[2])) h1 = ceil(q[4].y-eps);
         else h1 = ceil(max(p[1].y,p[2].y)-eps);
    
         printf("%d
    ",(h1-h0)*(w1-w0));
         return 0;
     }
  • 相关阅读:
    Codechef EDGEST 树套树 树状数组 线段树 LCA 卡常
    BZOJ4319 cerc2008 Suffix reconstruction 字符串 SA
    Codechef STMINCUT S-T Mincut (CodeChef May Challenge 2018) kruskal
    Codeforces 316G3 Good Substrings 字符串 SAM
    Codechef CHSIGN Change the Signs(May Challenge 2018) 动态规划
    BZOJ1396 识别子串 字符串 SAM 线段树
    CodeForces 516C Drazil and Park 线段树
    CodeForces 516B Drazil and Tiles 其他
    CodeForces 516A Drazil and Factorial 动态规划
    SPOJ LCS2
  • 原文地址:https://www.cnblogs.com/SunQi-lvbu/p/7846445.html
Copyright © 2011-2022 走看看