28. 同心圆

description

今天助教在做一道美术题:

现在有 ​个圆,均以坐标原点为圆心,半径分别为 ​,然后还有 ​条过圆心的直线,直线怎么画才能让看图的人视觉效果最好?

助教很快的回答说:

那当然是直接等分圆好呀。就是 ​条线会和每个圆产生 ​个交点,让相邻两个点之间的距离相等呀。

于是就有了这样的图片:


老师看到这个图片以后觉得很美,想知道一个问题:

这些圆和线有很多交点,这些交点两两之间的最短路之和是多少?

输入格式

输入共一行,包括两个整数 ​,分别表示同心圆的个数和直线的条数。

输出格式

输出一个浮点数,表示这些圆和线的交点两两之间的最短路之和。如果你的答案是 ​,标准答案是 ​,当且仅当 ​时,你将通过此题。

样例说明

总距离为 ​。


 测试输入 期待的输出 时间限制 内存限制 额外进程
测试用例 1以文本方式显示
  1. 1 3↵
以文本方式显示
  1. 30.2831853072↵
1秒64M0

题目不知道为什么显示不完整了,贴个图吧
在这里插入图片描述

code

直接看代码吧,更重要的是这个公式

#include <cstdio>
#include <iostream>

using namespace std;
const double pi = 3.141592653589793238;
int main()
{
    double n, m, i, j;
    double hu;  //弧长
    cin >> n >> m;

    double result = 0;
    /*
    下标从1开始,第i个圆的半径为i,l[i]保存的是第i个圆上的任意一点
    到其他各点,不包括圆心的距离之和,
    lsum[i]保存的是第i个圆上所有点到其他各点(不包括圆心)的距离之和
    */
    double l[(int)(n + 1)];
    double lsum[(int)(n + 1)];

    for(i = 1; i <= n; i++) {
        int i0 = (int)i;
        lsum[i0] = 0;
        for(j = 1; j < m; j++) {
            hu = j * pi * i / m;
            if(hu >= 2 * i)
                lsum[i0] += 2 * i;
            else
                lsum[i0] += hu;
        }
        l[i0] = 2 * lsum[i0] + 2 * i;
        lsum[i0] = m * l[i0];
    }
    if(m != 1)
        result += lsum[1] + 2 * m;
    else
        result += lsum[1];

    if(n == 1) {
        printf("%.10lf\n", result);
        return 0;
    }
    for(i = 2; i <= n; i++) {
        if(m != 1)
            result += lsum[(int)i] + 2 * m * i + 2 * m * m * i * (i - 1);
        else
            result += lsum[(int)i] + 2 * m * m * i * (i - 1);
        for(j = i - 1; j >= 1; j--)
            result += 2 * m * l[(int)j];
    }
    printf("%.10lf\n", result);

    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值