立体几何Journey to Jupiter Gym - 101991J 立体几何模板

Posted suut

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了立体几何Journey to Jupiter Gym - 101991J 立体几何模板相关的知识,希望对你有一定的参考价值。

https://cn.vjudge.net/problem/Gym-101991J

题目很长,其实就是给你一个正三角形,它的中心穿过Z轴,并且告诉你它的法向量,边长和定点A的坐标,让你求A,B,C到Z轴上一点H的距离。

技术分享图片

 

题解:高考向量题,考虑正三角形,我是把OB拆成OD加DB,OD=-OA/2,DB可以通过连立三个方程得到(它垂直于AO和法向量,他的长度为L/2)

技术分享图片

坑:我解方程的时候写错了orz然后y写成xorz  最后没考虑逆时针输出orz(这里要用叉积判一下,OA X OB 的方向要与法向量同)

 

#include<algorithm>
#include<iostream>
#include<stdlib.h>
#include<string.h>
#include<math.h>
#include<stdio.h>
#include<vector>
#include<queue>
#include<string>
#include<ctime>
#include<stack>
#include<map>
#include<set>
#include<list>
using namespace std;
#define rep(i,j,k) for(int i = (int)j;i <= (int)k;i ++)
#define per(i,j,k) for(int i = (int)j;i >= (int)k;i --)
#define debug(x) cerr<<#x<<" = "<<(x)<<endl
#define mmm(a,b) memset(a,b,sizeof(a))
#define pb push_back
//#define x first
//#define y second

typedef double  db;
typedef long long ll;
const int MAXN = 100010;;
const int maxn = MAXN;
struct V {
    db x, y,z;
    V() {}
    void sc() { scanf("%lf%lf", &x, &y); }
    V(db a, db b) : x(a), y(b) { }
    V operator+(V o) { return V(x + o.x, y + o.y); }
    V operator-(V o) { return V(x - o.x, y - o.y); }
    db L() { return sqrt(x * x + y * y); }
    V N() {
        db l = L();
        return V(x / l, y / l);
    }
    V rot(db th) { return V(x * cos(th) - y * sin(th), x * sin(th) + y * cos(th)); }
    V operator*(db z) { return V(x * z, y * z); }
    db operator*(V o) { return x * o.x + y * o.y; }
    db operator|(V o) { return x * o.y - o.x * y; }
    void pr() { printf("%lf %lf
", x, y); }
} p[maxn];


//三维几何函数库

#define eps 1e-8
#define zero(x) (((x)>0?(x):-(x))<eps)
struct point3 { db x, y, z; };
struct line3 { point3 a, b; };
struct plane3 { point3 a, b, c; };

//计算cross product U x V
point3 xmult(point3 u, point3 v) {
    point3 ret;
    ret.x = u.y*v.z - v.y*u.z;
    ret.y = u.z*v.x - u.x*v.z;
    ret.z = u.x*v.y - u.y*v.x;
    return ret;
}

//计算dot product U . V
db dmult(point3 u, point3 v) {
    return u.x*v.x + u.y*v.y + u.z*v.z;
}

//矢量差 U - V
point3 subt(point3 u, point3 v) {
    point3 ret;
    ret.x = u.x - v.x;
    ret.y = u.y - v.y;
    ret.z = u.z - v.z;
    return ret;
}
point3 addt(point3 u, point3 v) {
    point3 ret;
    ret.x = u.x + v.x;
    ret.y = u.y + v.y;
    ret.z = u.z + v.z;
    return ret;
}

//取平面法向量
point3 pvec(plane3 s) {
    return xmult(subt(s.a, s.b), subt(s.b, s.c));
}
point3 pvec(point3 s1, point3 s2, point3 s3) {
    return xmult(subt(s1, s2), subt(s2, s3));
}

//两点距离,单参数取向量大小
db distance(point3 p1, point3 p2) {
    return sqrt((p1.x - p2.x)*(p1.x - p2.x) + (p1.y - p2.y)*(p1.y - p2.y) + (p1.z - p2.z)*(p1.z - p2.z));
}

//向量大小
db vlen(point3 p) {
    return sqrt(p.x*p.x + p.y*p.y + p.z*p.z);
}


int main() {
    freopen("jupiter.in", "r", stdin);
    int t; cin >> t;
    while (t--) {
        point3 N, A;
        db l, h;
        scanf("%lf%lf%lf%lf%lf%lf%lf%lf", &N.x, &N.y, &N.z, &A.x, &A.y, &A.z, &l, &h);
        //scanf("%f%f%f%f%f%f%f%f", &N.x, &N.y, &N.z, &A.x, &A.y, &A.z, &l, &h);
        //cin >> N.x >> N.y >> N.z >> A.x >> A.y >> A.z >> l >> h;
        point3 H = { 0.,0.,-h };
        db La, Lb, Lc;
        
        db up = N.z*A.x - A.z*N.x;
        db under = N.y*A.x - A.y*N.x;
        db coy = -up / under;
        db cox =( N.z + N.y*coy)/(-N.x);
        cox = (A.z + A.y*coy) / (-A.x);
        db zz=l*l / 4.0/(coy*coy + cox*cox + 1.0) ;
        db z = l/sqrt(coy*coy + cox * cox + 1.0)/2.0;
        //db z = l / 2.0 / (coy + cox + 1.0);
        db x = cox * z;
        db y = coy * z;
        point3 b = { x,y,z };
        point3 c = { -x,-y,-z };
        point3 t = xmult(A, b);
        if (t.z*N.z > 0);
        else swap(b, c);
        point3 unA = { -A.x / 2.,-A.y / 2.,-A.z / 2. };
        point3 B = addt(unA, b);
        point3 C = addt(unA, c);
        La = distance(A, H);
        Lb = distance(B, H);
        Lc = distance(C, H);
        //if (N.z < 0)swap(Lb, Lc);
        printf("%.6lf %.6lf %.6lf
", La,Lb,Lc);
        

    }
    //cin >> t;
}
/*
2
13 -18 1 7 5 -1 15 12
-12 -17 1 7 -5 -1 15 3

2
13 -18 1 7 5 -1 15 12
-12 -17 1 7 -5 -1 15 3
*/

 

以上是关于立体几何Journey to Jupiter Gym - 101991J 立体几何模板的主要内容,如果未能解决你的问题,请参考以下文章

[POI2005]A Journey to Mars 单调队列

NEERC17 J Journey from Petersburg to Moscow

Gym:101630J - Journey from Petersburg to Moscow(最短路)

The Go Blog Getting to Go: The Journey of Go's Garbage Collector

J. Journey to the “The World’s Start”(二分线段树dp)

Journey Planning