网上都评价说这题不难,没什么算法,是道水题,可是我看了别人的代码后,感觉收获还是比较大的,就发了。
      这题先是求积分,高中物理都能搞定的,把dl=rdă代入就能求得I=ă*k*h,其中ă是每条边对原点夹的角,比如对边AB,它的ă就是<AOB。那么下面的问题就转化为整个图形对原点所夹的角的最大值,这里可能有个问题,比如对于一个螺旋型的Fence,原点在中心,那么可能求出的夹角大于2*PI,由于Fence是不能透光、反射、散射的,因此最大值只能为2*PI。又由于Fence不能经过原点,因此每条边的夹角在-PI~PI之间,这里求整个图形对原点所夹的角用了一个很强的方法,可以保证无论从哪个点开始算,只要是按顺序,它一定能求得最大的角度(我领悟了半天啊),而且min一定要初始化为0而不是2*PI等大于0的数,考虑下原点在图形内部的情况就知道了~~至于正确性,可以自已画个图就能理解了~~
      下面是我的实现代码,参考了网上代码~~
#include <iostream>
#include <cmath>
using namespace std;
#define PI 3.1415926

double Angle( double x0, double y0, double x1, double y1 ){
     double a= atan2(y0,x0);
     double b= atan2(y1,x1);
     if( b-a> PI ) a+= 2*PI;    //将夹角映射到-PI~PI之间
     if( a-b> PI ) b+= 2*PI;
     return a-b;
}


int main(){
    double h, k, x[101], y[101], max= 0, min= 0, sum= 0;
    int n, i;
    scanf("%lf%lf%d",&k,&h,&n);
    for( i= 0; i< n; i++ )
        scanf("%lf%lf",&x[i],&y[i]);
    x[n]= x[0], y[n]= y[0];

    for( i= 0; i< n; i++ ){      //精髓啊
        sum+= Angle(x[i],y[i],x[i+1],y[i+1]);
        if( sum< min )    min= sum;
        if( sum> max )    max= sum;

        if( max-min>= 2*PI ){
            max= min+ 2*PI;
            break;
        }
    }
    printf("%.2lf\n",(max-min)*k*h);
    return 0;
} 
	posted on 2009-06-26 10:58 
古月残辉 阅读(2473) 
评论(3)  编辑 收藏 引用  所属分类: 
计算几何