poj 3384

题目概述

按顺时针序给定一个简单凸N边形的所有顶点坐标x,y,以及圆的半径R,将两个如此的圆放在多边形中,求圆心的坐标,使得两圆覆盖多边形的面积最大
圆只能与多边形相切,但两个圆可以相交,数据确保多边形的大小足够装下一个圆

时限

2000ms/6000ms

输入

第一行两个正整数N,R,其后N行,每行两个整数x,y,输入到EOF结束

限制

3<=N<=100;1<=R<=1000;-1000<=x,y<=1000

输出

每行四个至少保留4位小数的浮点数,描述两个可行的圆心坐标,答案可能会有多种,输出任意一种即可

样例输入

5 2
-2 0
-5 3
0 8
7 3
5 0

4 3
0 0
0 8
10 8
10 0

4 1
0 0
0 2
2 2
2 0

4 1
0 0
0 3
3 3
3 0

4 1
0 0
0 4
4 4
4 0

4 1
0 0
0 2
4 2
4 0

4 1
0 0
0 2
3 2
3 0

4 1
0 0
0 4
2 4
2 0

4 1
0 0
0 3
2 3
2 0

3 1
0 0
0 4
3 0

3 1
0 0
0 8
6 0

3 3
0 0
0 16
12 0

5 3
0 0
0 14
3 12
9 4
9 0

5 3
0 0
0 14
3 12
9 4
11 0

30 85
298 179
291 159
281 141
267 126
250 113
231 105
210 101
190 101
169 105
150 113
133 126
119 141
109 159
102 179
100 200
102 221
109 241
119 259
133 274
150 287
169 295
190 299
210 299
231 295
250 287
267 274
281 259
291 241
298 221
300 200

6 5
233 161
156 226
123 264
167 239
244 174
277 136

7 8
243 154
177 207
128 255
134 261
189 222
253 166
277 136

95 45
745 505
764 470
780 431
792 392
800 350
805 310
807 265
804 218
798 172
789 126
777 80
761 35
740 -16
719 -61
691 -112
663 -156
632 -201
598 -245
560 -290
522 -331
477 -375
435 -413
387 -452
337 -489
295 -517
241 -551
192 -578
135 -607
82 -630
29 -651
-23 -668
-74 -682
-130 -695
-179 -703
-237 -709
-284 -712
-336 -711
-385 -707
-430 -700
-470 -692
-517 -677
-553 -663
-595 -643
-631 -620
-661 -597
-691 -570
-719 -539
-740 -510
-761 -475
-779 -436
-793 -398
-803 -358
-809 -317
-812 -276
-812 -232
-808 -187
-801 -142
-789 -93
-775 -47
-756 5
-735 50
-710 99
-686 140
-653 191
-620 236
-585 279
-548 321
-504 366
-464 404
-415 445
-373 478
-325 512
-272 547
-224 576
-166 606
-120 628
-62 652
-10 671
45 687
101 701
151 711
201 718
255 722
303 723
349 721
400 716
445 708
492 695
531 681
569 665
607 643
637 623
669 597
699 567
723 538

95 500
745 505
764 470
780 431
792 392
800 350
805 310
807 265
804 218
798 172
789 126
777 80
761 35
740 -16
719 -61
691 -112
663 -156
632 -201
598 -245
560 -290
522 -331
477 -375
435 -413
387 -452
337 -489
295 -517
241 -551
192 -578
135 -607
82 -630
29 -651
-23 -668
-74 -682
-130 -695
-179 -703
-237 -709
-284 -712
-336 -711
-385 -707
-430 -700
-470 -692
-517 -677
-553 -663
-595 -643
-631 -620
-661 -597
-691 -570
-719 -539
-740 -510
-761 -475
-779 -436
-793 -398
-803 -358
-809 -317
-812 -276
-812 -232
-808 -187
-801 -142
-789 -93
-775 -47
-756 5
-735 50
-710 99
-686 140
-653 191
-620 236
-585 279
-548 321
-504 366
-464 404
-415 445
-373 478
-325 512
-272 547
-224 576
-166 606
-120 628
-62 652
-10 671
45 687
101 701
151 711
201 718
255 722
303 723
349 721
400 716
445 708
492 695
531 681
569 665
607 643
637 623
669 597
699 567
723 538

100 800
-747 505
-710 555
-670 606
-628 652
-583 696
-539 734
-489 773
-436 809
-383 841
-330 868
-277 892
-223 912
-162 931
-107 944
-45 954
10 960
67 962
123 961
182 955
236 947
296 933
348 917
404 896
457 871
499 848
550 815
593 783
640 743
680 703
718 660
752 616
782 571
813 519
837 470
862 409
879 358
895 297
907 238
915 180
919 128
920 61
918 7
911 -61
901 -124
888 -178
871 -238
850 -300
828 -352
801 -409
767 -468
735 -519
698 -570
660 -617
620 -660
576 -704
530 -745
483 -781
430 -817
380 -848
320 -879
268 -902
210 -923
160 -938
97 -954
39 -963
-17 -969
-74 -972
-135 -970
-189 -965
-250 -955
-300 -944
-353 -928
-410 -906
-459 -884
-514 -853
-556 -827
-605 -790
-647 -754
-689 -713
-728 -668
-761 -626
-792 -579
-822 -527
-846 -477
-867 -426
-888 -366
-903 -311
-916 -248
-923 -191
-928 -134
-929 -70
-927 -16
-920 46
-910 110
-897 166
-880 229
-858 290
-837 341
-806 404
-780 452

100 880
-749 500
-716 546
-678 592
-639 633
-597 672
-556 706
-508 741
-458 772
-408 800
-357 823
-306 843
-255 860
-196 875
-143 884
-82 892
-30 895
26 895
81 891
139 884
192 874
251 858
302 841
358 819
410 794
453 771
504 738
547 707
595 667
635 628
674 587
709 545
740 501
772 451
797 405
824 347
843 298
862 241
876 185
885 131
892 82
895 19
895 -31
891 -94
884 -152
874 -203
859 -258
841 -315
822 -362
797 -414
767 -468
737 -515
704 -560
669 -603
632 -642
590 -681
547 -717
503 -749
452 -780
404 -807
347 -833
297 -853
241 -871
194 -883
133 -894
77 -901
22 -904
-33 -904
-93 -900
-146 -894
-206 -882
-255 -869
-308 -852
-364 -830
-412 -807
-468 -776
-509 -750
-559 -714
-601 -678
-644 -638
-684 -595
-717 -554
-750 -509
-781 -459
-807 -412
-830 -364
-852 -307
-869 -254
-884 -195
-894 -142
-900 -88
-904 -29
-904 22
-900 79
-893 139
-883 191
-868 248
-849 305
-831 351
-803 409
-780 452

100 1
-749 500
-716 546
-678 592
-639 633
-597 672
-556 706
-508 741
-458 772
-408 800
-357 823
-306 843
-255 860
-196 875
-143 884
-82 892
-30 895
26 895
81 891
139 884
192 874
251 858
302 841
358 819
410 794
453 771
504 738
547 707
595 667
635 628
674 587
709 545
740 501
772 451
797 405
824 347
843 298
862 241
876 185
885 131
892 82
895 19
895 -31
891 -94
884 -152
874 -203
859 -258
841 -315
822 -362
797 -414
767 -468
737 -515
704 -560
669 -603
632 -642
590 -681
547 -717
503 -749
452 -780
404 -807
347 -833
297 -853
241 -871
194 -883
133 -894
77 -901
22 -904
-33 -904
-93 -900
-146 -894
-206 -882
-255 -869
-308 -852
-364 -830
-412 -807
-468 -776
-509 -750
-559 -714
-601 -678
-644 -638
-684 -595
-717 -554
-750 -509
-781 -459
-807 -412
-830 -364
-852 -307
-869 -254
-884 -195
-894 -142
-900 -88
-904 -29
-904 22
-900 79
-893 139
-883 191
-868 248
-849 305
-831 351
-803 409
-780 452

5 20
-266 131
-261 173
-255 197
-194 198
-205 151

10 44
-201 159
-220 182
-218 209
-143 268
-39 344
72 414
89 415
99 366
20 277
-75 208

20 630
-636 -285
-707 -125
-722 29
-719 153
-705 300
-459 632
-413 660
-329 692
-227 727
361 661
471 590
679 358
768 202
712 -314
575 -499
537 -539
242 -712
165 -713
-105 -702
-402 -547

18 44
-46 44
-110 0
-136 28
-274 209
-337 295
-336 318
-322 333
-208 421
-126 484
-50 540
-43 544
-29 545
64 424
120 351
198 247
196 232
193 225
0 77

18 190
-46 44
-110 0
-136 28
-274 209
-337 295
-336 318
-322 333
-208 421
-126 484
-50 540
-43 544
-29 545
64 424
120 351
198 247
196 232
193 225
0 77

14 390
-350 247
-278 349
250 667
331 713
470 693
778 212
803 172
870 52
893 -80
838 -130
125 -569
67 -483
-191 -77
-297 95

11 390
142 -277
58 -425
-45 -401
-636 -227
-733 153
-628 574
-549 659
-445 744
117 552
360 446
177 -185

17 390
-143 -140
-190 -78
-231 -22
-248 174
-250 228
-217 364
-92 491
291 648
480 586
622 449
636 351
649 -36
536 -213
359 -286
329 -290
181 -284
-57 -230

27 390
-87 -208
-178 -121
-209 -65
-243 13
-254 63
-263 134
-266 212
-210 380
-202 397
-130 497
-114 518
-113 519
-79 541
-12 582
335 637
392 634
519 559
648 409
674 320
704 94
693 -13
646 -84
505 -242
326 -317
294 -322
58 -291
-50 -238

20 490
-589 -613
-663 -546
-787 -368
-839 -251
-876 -12
-882 66
-858 227
-781 441
-753 487
-710 554
-615 661
-19 845
73 826
644 662
849 354
863 -241
670 -553
350 -806
68 -793
-26 -783

样例输出

-2.1715728753 3.0000000000 4.2617090669 2.4981148759
3.0000000000 5.0000000000 7.0000000000 3.0000000000
1.0000000000 1.0000000000 1.0000000000 1.0000000000
1.0000000000 2.0000000000 2.0000000000 1.0000000000
1.0000000000 3.0000000000 3.0000000000 1.0000000000
1.0000000000 1.0000000000 3.0000000000 1.0000000000
1.0000000000 1.0000000000 2.0000000000 1.0000000000
1.0000000000 3.0000000000 1.0000000000 1.0000000000
1.0000000000 2.0000000000 1.0000000000 1.0000000000
1.0000000000 1.0000000000 1.0000000000 1.0000000000
1.0000000000 5.0000000000 4.0000000000 1.0000000000
3.0000000000 7.0000000000 6.0000000000 3.0000000000
3.0000000000 7.0000000000 6.0000000000 3.0000000000
3.0000000000 7.0000000000 6.0000000000 3.0000000000
193.0006411509 187.1218295621 206.9993588491 212.8781704379
145.9308210170 245.2204058181 254.0691789830 154.7795941819
241.0504825763 165.8256819330 167.7464216802 227.2635873433
-683.9772456803 -510.6396968654 686.8485759249 511.1022324147
297.0975269711 222.7685366387 -302.4372025734 -211.5529913372
91.5764285376 158.7584647666 -103.9981603080 -165.7679246168
-19.1568267359 7.6846327740 9.2412215727 -19.3123152000
-195.7927555570 874.0208769767 193.7873033719 -882.0222261318
-242.4332577840 159.7743467537 -219.3190801407 177.5822458434
-98.3582657396 246.1262937844 -8.4145450917 311.2694981965
-90.8068226158 70.6981456695 105.6936542367 -61.5939272551
-288.5122507008 303.2658847078 145.3303992705 243.8928009727
-73.8238956593 259.8223004766 -70.4371016325 287.0870685889
132.7097497858 141.0883685620 409.5428845216 64.1917022085
-163.6741892181 40.4911661579 -298.8917839509 281.9523959649
147.8500507412 123.4339313246 250.5194502971 209.9109003884
136.8827301375 117.5159109329 293.4333801212 223.1632820376
-364.7456759095 -111.5871484837 362.4732720429 200.6220299555

讨论

计算几何,半平面交,额先说说上面这一堆数据,这一共是32组,从官方那里挖来的,使用的时候需要单独写一个程序,算一下两点的距离,原题说要坐标精确到1e-4,却没说两点间距离要精确到多少,不过应该不会差太多
算法部分思路和上一个题poj 3525有些类似,这个题也需要算偏移量,不过只需要算一遍,然后求半平面交,然后从可行域中枚举所有点,找出最远的一对即可
既然有心思找数据,说明额肯定是又莫名WA了,是的,这次败在精度上,或者说不细心吧,不难发现,前面额做的有几道题里出现过signal函数,判断浮点数正负的,而到了半平面交这部分又消失了,额感觉不会有那么极端的数据吧,结果这回真遇到了,上面这32组数据中有一组一共就3条线,最后的可行域是三条线偏移后相交得到的一个点,只有一个点,到额这里,由于没有使用符号函数,产生了一个1e-15级的浮点误差,然后被判定为没有可行域,程序爆炸(因为没有初始化也没有赋值就被输出了),然而额之前交上去的没有爆炸,而是返回两个WA
再来简单说一下为什么不能直接枚举所有点而要先求一次半平面交,其实猜也能猜到,无法保证所有交点构成的新图形的形状,最后枚举所得结果可能并不合法,很可惜额水平有限,无法展开来说明,不过上面有几组数据确实是这样,可以画图看一下

题解状态

212K,47MS,C++,3263B

题解代码

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
using namespace std;
#define INF 0x3f3f3f3f  
#define MAXN 300
#define memset0(a) memset(a,0,sizeof(a))
#define EPS 1e-8

struct Pt//point 点的结构
{
    double x, y;
}pts[MAXN], pt1[MAXN], pt2[MAXN];//存放原始点 以及半平面交两个辅助数组
int hpt1, hpt2;//halfplane_point 辅助数组中点的数量
int N, R;//点总数 半径大小
double d[MAXN], ofx[MAXN], ofy[MAXN];//distance 两点间距离 便于求两个方向的偏移量 offset_x offset_y 两个方向的偏移量 具体的使用方法和poj 3525相同 通过移动点来移动线段
int signal(double a)//符号函数
{
    if (abs(a) < EPS)
        return 0;
    return a > 0 ? 1 : -1;
}
double xp(double x1, double y1, double x2, double y2, double x3, double y3)//向量积 曾经写过用三个Pt而不是六个double的 不过不习惯
{
    return (x1 - x2)*(y3 - y2) - (y1 - y2)*(x3 - x2);
}
double dis(double x1, double y1, double x2, double y2)//两点间距离
{
    return sqrt((x1 - x2)*(x1 - x2) + (y1 - y2)*(y1 - y2));
}
Pt point_of_intersection(double x1, double y1, double x2, double y2, double x3, double y3, double x4, double y4)//求交点坐标 这个非常好记 用了一次就差不多背过了
{
    Pt poi;//这名字不想解释
    double Sabc = xp(x3, y3, x1, y1, x2, y2);
    double Sabd = xp(x4, y4, x1, y1, x2, y2);//两个三角形有向面积的二倍 作为等比分点公式的比例
    poi.x = (Sabc*x4 - Sabd*x3) / (Sabc - Sabd);
    poi.y = (Sabc*y4 - Sabd*y3) / (Sabc - Sabd);//等比分点公式 由于是有向面积 所以用减的
    return poi;
}
double offsetx(double r, int p)//水平偏移量 r是题目给的半径 p是点在pts数组的下标 说明什么的和poj 3525都一样
{
    return (pts[(p + 1) % N].y - pts[p].y)*r / d[p];
}
double offsety(double r, int p)//竖直偏移量
{
    return (pts[p].x - pts[(p + 1) % N].x)*r / d[p];
}
void fun()
{
    for (int p = 0; p < N; p++)
        scanf("%lf%lf", &pts[p].x, &pts[p].y);//input
    for (int p = 0; p < N; p++) {
        d[p] = dis(pts[p].x, pts[p].y, pts[(p + 1) % N].x, pts[(p + 1) % N].y);//算出两点间距离
        ofx[p] = offsetx(R, p);
        ofy[p] = offsety(R, p);//将半径造成的偏移量正交分解为两个方向
    }
    for (int p = 0; p < N; p++)
        pt1[p] = point_of_intersection(pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p], pts[(p + 1) % N].x + ofx[(p + 1) % N], pts[(p + 1) % N].y + ofy[(p + 1) % N], pts[(p + 2) % N].x + ofx[(p + 1) % N], pts[(p + 2) % N].y + ofy[(p + 1) % N]);//将偏移后的线段的交点求出来放到点集1中 同一个点在不同线段上所带的偏移量也不同
    hpt1 = N;//初始化点集1中点数
    for (int p = 0; p < N; p++) {//枚举相邻两个点做判定线
        hpt2 = 0;//点集2初始没有点
        for (int i = 0; i < hpt1; i++) {//枚举点集1中的点
            if (signal(xp(pt1[i].x, pt1[i].y, pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p])) >= 0)//如果在判定线右侧 注意这里以及后面都加上了signal函数
                pt2[hpt2++] = pt1[i];//放到点集2
            else {//否则
                if (signal(xp(pt1[(i - 1 + hpt1) % hpt1].x, pt1[(i - 1 + hpt1) % hpt1].y, pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p]))>0)//如果点集1中前一个点和这个点所成直线与判定线交点在判定线右侧
                    pt2[hpt2++] = point_of_intersection(pt1[i].x, pt1[i].y, pt1[(i - 1 + hpt1) % hpt1].x, pt1[(i - 1 + hpt1) % hpt1].y, pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p]);//把交点放到点集2
                if (signal(xp(pt1[(i + 1) % hpt1].x, pt1[(i + 1) % hpt1].y, pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p]))>0)//同样处理后一个点
                    pt2[hpt2++] = point_of_intersection(pt1[i].x, pt1[i].y, pt1[(i + 1) % hpt1].x, pt1[(i + 1) % hpt1].y, pts[p].x + ofx[p], pts[p].y + ofy[p], pts[(p + 1) % N].x + ofx[p], pts[(p + 1) % N].y + ofy[p]);
            }
        }
        for (int p = 0; p < hpt2; p++)
            pt1[p] = pt2[p];
        hpt1 = hpt2;//将点集2赋给点集1
    }
    double most = -INF, x1, y1, x2, y2;//由于没有初始化 因而直接输出会程序爆炸
    for (int p = 0; p < hpt1; p++)//下面通过枚举找出最远的两个点
        for (int i = p + 1; i < hpt1; i++) {
            double d = dis(pt1[p].x, pt1[p].y, pt1[i].x, pt1[i].y);
            if (d > most) {
                most = d;
                x1 = pt1[p].x, y1 = pt1[p].y;
                x2 = pt1[i].x, y2 = pt1[i].y;
            }
        }
    printf("%lf %lf %lf %lf\n", x1, y1, x2, y2);//output
}
int main(void)
{
    //freopen("vs_cin.txt", "r", stdin);
    //freopen("vs_cout.txt", "w", stdout);

    while (~scanf("%d%d", &N, &R))//input
        fun();
}

EOF

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值