计算几何 2017.4.5


2、UVa 11178 Morley's Theorem

参考:《算法竞赛入门经典-训练指南》P259

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <vector>
#include <stack>
#include <map>
#include <set>
#include <cmath>
#include <cctype>
#include <ctime>
#include <cassert>

using namespace std;

#define REP(i, n) for (int i = 0; i < (n); ++i)

struct Point {
  double x, y;
  Point(double x = 0.0, double y = 0.0):x(x),y(y) {}
};
typedef Point Vector;

const double INF = 1e20;
const double eps = 1e-10;
const double PI = acos(-1.0);
Point A, B, C, D, E, F;
int N;

Point operator + (const Point& a, const Vector& b) { return Point{a.x + b.x, a.y + b.y}; }
Vector operator - (const Point& a, const Point& b) { return Vector(a.x - b.x, a.y - b.y); }
Vector operator * (const Vector& a, double k) { return Vector{a.x * k, a.y * k}; }
double dot(const Vector& a, const Vector& b) { return a.x * b.x + a.y * b.y; }
double length(const Vector& a) { return sqrt(dot(a, a)); }
double angle(const Vector& a, const Vector& b) { return acos(dot(a, b) / length(a) / length(b)); }
double cross(const Vector& a, const Vector& b) { return a.x * b.y - a.y * b.x; }
Point read_point() { double x, y; scanf("%lf %lf", &x, &y); return Point{x, y}; }
Point line_intersection(const Point& p, const Vector& v, const Point& q, const Vector& w) {
    Vector u = p - q; double t = cross(w, u) / cross(v, w); return p + v * t;
}
Vector rotate(const Vector& a, double rad) {
    return Vector{a.x * cos(rad) - a.y * sin(rad), a.x * sin(rad) + a.y * cos(rad)};
}
Point get_D(Point a, Point b, Point c) {
    Vector v1 = c - b; double a1 = angle(v1, a - b); v1 = rotate(v1, a1 / 3.0);
    Vector v2 = b - c; double a2 = angle(a - c, v2); v2 = rotate(v2, -a2 / 3.0);
    return line_intersection(b, v1, c, v2);
}

int main() {
#ifdef __AiR_H
    freopen("in.txt", "r", stdin);
//    freopen("out.txt", "w", stdout);
#endif // __AiR_H
    scanf("%d", &N);
    while (N--) {
        A = read_point(); B = read_point(); C = read_point();
        D = get_D(A, B, C); E = get_D(B, C, A); F = get_D(C, A, B);
        printf("%.6f %.6f %.6f %.6f %.6f %.6f\n", D.x, D.y, E.x, E.y, F.x, F.y);
    }
#ifdef __AiR_H
    printf("Time used = %.2fs\n", (double)clock() / CLOCKS_PER_SEC);
#endif // __AiR_H
    return 0;
}


3、POJ 1269 Intersecting Lines

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <vector>
#include <stack>
#include <map>
#include <set>
#include <cmath>
#include <cctype>
#include <ctime>
#include <cassert>

using namespace std;

#define REP(i, n) for (int i = 0; i < (n); ++i)

struct Point {
  double x, y;
  Point(double x = 0.0, double y = 0.0):x(x),y(y) {}
};
typedef Point Vector;
struct Seg { Point a, b; };

const double INF = 1e20;
const double eps = 1e-10;
const double PI = acos(-1.0);
int T;
Seg A, B;

Point operator + (const Point& a, const Vector& b) { return Point(a.x + b.x, a.y + b.y); }
Vector operator - (const Point& a, const Point& b) { return Vector(a.x - b.x, a.y - b.y); }
Vector operator * (const Vector& a, double k) { return Vector(a.x * k, a.y * k); }
double cross(const Vector& a, const Vector& b) { return a.x * b.y - a.y * b.x; }
Point read_point() { double x, y; scanf("%lf %lf", &x, &y); return Point(x, y); }
Seg read_seg() { return Seg{read_point(), read_point()}; }
bool is_parallel(const Seg& p, const Seg& q) {
    return (abs((p.a.y - p.b.y) * (q.a.x - q.b.x) - (p.a.x - p.b.x) * (q.a.y - q.b.y)) < eps) ? true : false;
}
Point line_intersection(const Point& p, const Vector& v, const Point& q, const Vector& w) {
    Vector u = p - q; double t = cross(w, u) / cross(v, w); return p + v * t;
}


int main() {
#ifdef __AiR_H
    freopen("in.txt", "r", stdin);
//    freopen("out.txt", "w", stdout);
#endif // __AiR_H
    scanf("%d", &T);
    printf("INTERSECTING LINES OUTPUT\n");
    while (T--) {
        A = read_seg(); B = read_seg();
        if (is_parallel(A, B)) {
            if (is_parallel(A, Seg{A.a, B.a})) { printf("LINE\n"); }
            else { printf("NONE\n"); }
        } else {
            Point ans = line_intersection(A.a, A.b - A.a, B.a, B.b - B.a);
            printf("POINT %.2f %.2f\n", ans.x, ans.y);
        }
    }
    printf("END OF OUTPUT\n");
#ifdef __AiR_H
    printf("Time used = %.2fs\n", (double)clock() / CLOCKS_PER_SEC);
#endif // __AiR_H
    return 0;
}


4、POJ 1127 Jack Straws

参考:《挑战程序设计竞赛》《算法竞赛入门经典-训练指南 》

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <vector>
#include <stack>
#include <map>
#include <set>
#include <cmath>
#include <cctype>
#include <ctime>
#include <cassert>

using namespace std;

#define REP(i, n) for (int i = 0; i < (n); ++i)

struct Point {
  double x, y;
  Point(double x = 0.0, double y = 0.0):x(x),y(y) {}
};
typedef Point Vector;
struct Seg { Point a, b; };

const double INF = 1e20;
const double eps = 1e-10;
const double PI = acos(-1.0);
int n;
bool vis[20], G[20][20];
bool flag = false;

Point operator + (const Point& a, const Vector& b) { return Point(a.x + b.x, a.y + b.y); }
Vector operator - (const Point& a, const Point& b) { return Vector(a.x - b.x, a.y - b.y); }
Vector operator * (const Vector& a, double k) { return Vector(a.x * k, a.y * k); }
double dot(const Vector& a, const Vector& b) { return a.x * b.x + a.y * b.y; }
double cross(const Vector& a, const Vector& b) { return a.x * b.y - a.y * b.x; }
Point read_point() { double x, y; scanf("%lf %lf", &x, &y); return Point(x, y); }
Seg read_seg() { return Seg{read_point(), read_point()}; }
int dcmp(double x) { if (fabs(x) < eps) return 0; else return x < 0 ? -1 : 1; }
bool on_seg(const Point& a, const Seg& p) {
    return dcmp(cross(p.a - a, p.b - a)) == 0 && dcmp(dot(p.a - a, p.b - a)) <= 0;
}
bool is_seg_intersect(const Seg& p, const Seg& q) {
    double c1 = cross(p.b - p.a, q.a - p.a), c2 = cross(p.b - p.a, q.b - p.a);
    double c3 = cross(q.b - q.a, p.a - q.a), c4 = cross(q.b - q.a, p.b - q.a);
    if (dcmp(c1) * dcmp(c2) < 0 && dcmp(c3) * dcmp(c4) < 0) { return true; }
    return on_seg(p.a, q) || on_seg(p.b, q) || on_seg(q.a, p) || on_seg(q.b, p);
}
void dfs(int u, int v) {
    if (flag) { return; }
    if (u == v) { flag = true; return; }
    REP(i, n) if (!vis[i] && G[u][i]) { vis[i] = true; dfs(i, v); }
}

int main() {
#ifdef __AiR_H
    freopen("in.txt", "r", stdin);
//    freopen("out.txt", "w", stdout);
#endif // __AiR_H
    int a, b; Seg seg[20];
    while (scanf("%d", &n) && n != 0) {
        memset(G, false, sizeof(G));
        REP(i, n) { seg[i] = read_seg(); }
        for (int i = 0; i < n - 1; ++i) for (int j = i + 1; j < n; ++j) {
            if (is_seg_intersect(seg[i], seg[j])) { G[i][j] = true; G[j][i] = true; }
        }
        while (scanf("%d %d", &a, &b) && !(a == 0 && b == 0)) {
            --a; --b; memset(vis, false, sizeof(vis)); flag = false; dfs(a, b);
            if (flag) { printf("CONNECTED\n"); }
            else { printf("NOT CONNECTED\n"); }
        }
    }
#ifdef __AiR_H
    printf("Time used = %.2fs\n", (double)clock() / CLOCKS_PER_SEC);
#endif // __AiR_H
    return 0;
}

5、POJ 2624 4th Point

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <vector>
#include <stack>
#include <map>
#include <set>
#include <cmath>
#include <cctype>
#include <ctime>
#include <cassert>

using namespace std;

#define REP(i, n) for (int i = 0; i < (n); ++i)

struct Point {
  double x, y;
  Point(double x = 0.0, double y = 0.0):x(x),y(y) {}
};
typedef Point Vector;
struct Seg { Point a, b; };

const double INF = 1e20;
const double eps = 1e-10;
const double PI = acos(-1.0);
Point A, B, C, D;

Point operator + (const Point& a, const Vector& b) { return Point(a.x + b.x, a.y + b.y); }
Vector operator - (const Point& a, const Point& b) { return Vector(a.x - b.x, a.y - b.y); }
Vector operator * (const Vector& a, double k) { return Vector(a.x * k, a.y * k); }
int dcmp(double x) { if (fabs(x) < eps) return 0; else return x < 0 ? -1 : 1; }

int main() {
#ifdef __AiR_H
    freopen("in.txt", "r", stdin);
//    freopen("out.txt", "w", stdout);
#endif // __AiR_H
    while (scanf("%lf %lf %lf %lf %lf %lf %lf %lf", &A.x, &A.y, &B.x, &B.y, &C.x, &C.y, &D.x, &D.y) != EOF) {
        Point ans, A_t, B_t, C_t;
        if (dcmp(A.x - C.x) == 0 && dcmp(A.y - C.y) == 0) { A_t = B; B_t = A; C_t = D; }
        else if (dcmp(B.x - C.x) == 0 && dcmp(B.y - C.y) == 0) { A_t = A; B_t = B; C_t = D; }
        else if (dcmp(A.x - D.x) == 0 && dcmp(A.y - D.y) == 0) { A_t = B; B_t = A; C_t = C; }
        else { A_t = A; B_t = B; C_t = C; }
        ans = A_t + (C_t - B_t);
        printf("%.3f %.3f\n", ans.x, ans.y);
    }
#ifdef __AiR_H
    printf("Time used = %.2fs\n", (double)clock() / CLOCKS_PER_SEC);
#endif // __AiR_H
    return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值