2021牛客寒假集训营第一场 E 三棱锥之刻

三棱锥之刻

https://ac.nowcoder.com/acm/contest/9981/E

分析

分情况讨论

  1. 中心到底面的距离 >= r, 答案为0。
  2. 中心到底面的距离 < r <= 中心到棱的中点的距离, 重叠的部分是圆。
  3. 棱的中点的距离 < r <= 中心到棱的顶点的距离,圆有一部分超过了三角形,计算超出的弧长,用的圆面积减去超过的,再乘以每个面。中间要算角度比较麻烦。
  4. 中心到棱的顶点的距离 <= r, 全部表面积。

全视图

图片说明

底面(情况3)

这张图片由 @KirbyOvO 大佬提供。

图片说明

#include<bits/stdc++.h>

using namespace std;

typedef long long LL;
typedef pair<int,int> PII;

#define x first
#define y second

const int N = 2e8, mod = 1e9 + 7;
const double PI = 3.1415926;

void solve()
{
    double a, r;
    cin >> a >> r;
    double rmax = a * sqrt(6) / 4.0;
    double rmin = sqrt(2) * a / 4.0;
    double t = sqrt(6) * a / 3 - rmax; // O2O3
    if(r <= t) cout << "0.000" << endl;
    else if(r <= rmin)
    {
        double ans = PI * (r * r - t * t) * 4;
        printf("%f\n", ans);
    }
    else if(r <= rmax)
    {
        double d = (r * r - t * t); // 斜边和半径
        double b = (d - a * a / 12) * 4; // 底边
        double cs = (d + d - b) / (2 * d); // cosx
        double tri = a / sqrt(12) * sqrt(b) / 2;
        double ans = (PI * d - 3 * (acos(cs) / 2 * d - tri)) * 4;
        printf("%f\n", ans);
    }
    else
    {
        double ans = a * sqrt(3) * a;
        printf("%f\n", ans);
    }
}

int main()
{
    /*ios::sync_with_stdio(false);
    cin.tie(0);cout.tie(0);
    int t;
    cin >> t;
    while(t --)*/
        solve();
}
全部评论
强捏
点赞 回复 分享
发布于 2023-07-20 21:28 新加坡

相关推荐

10-25 12:05
已编辑
湖南科技大学 Java
若梦难了:我有你这简历,已经大厂乱杀了
点赞 评论 收藏
分享
评论
3
收藏
分享
牛客网
牛客企业服务