• [洛谷P1452]Beauty Contest


    题目大意:给你$n$个点,求出其中最远点的距离

    题解:求出凸包,最远点一定都在凸包上,可以对每条边求出最远的点(可以双指针),然后求出和这条边的端点的距离,更新答案

    卡点:最开始对每个点求出最远点,但这样并不可以双指针怎么搞。

    C++ Code:

    #include <cstdio>
    #include <algorithm>
    #define maxn 50010
    int __X, __Y;
    inline int sqr(int x) {return x * x;}
    struct Point {
    	int x, y;
    	inline Point() {}
    	inline Point(int __x, int __y) : x(__x), y(__y) {}
    	inline int abs2() {return sqr(x) + sqr(y);}
    	inline friend Point operator - (const Point &lhs, const Point &rhs) {
    		return Point(lhs.x - rhs.x, lhs.y - rhs.y);
    	}
    	inline friend Point operator + (const Point &lhs, const Point &rhs) {
    		return Point(lhs.x + rhs.x, lhs.y + rhs.y);
    	}
    	inline friend int operator * (const Point &lhs, const Point &rhs) {
    		return lhs.x * rhs.y - rhs.x * lhs.y;
    	}
    	void writeln() {
    		printf("(%d, %d)
    ", x, y);
    	}
    } O, s[maxn], v[maxn];
    
    inline int abs2(const Point &x) {return sqr(x.x) + sqr(x.y);}
    inline int dis2(const Point &lhs, const Point &rhs) {return abs2(lhs - rhs);}
    inline int det(const Point O, const Point &lhs, const Point &rhs) {
    	return (lhs - O) * (rhs - O);
    }
    inline bool operator < (const Point &lhs, const Point &rhs) {
    	Point X = lhs - O, Y = rhs - O;
    	int tmp = X * Y;
    	return (tmp > 0) || (!tmp && abs2(X) > abs2(Y));
    }
    
    int n, miny, ans, tot;
    int main() {
    	scanf("%d", &n);
    	for (int i = 0; i < n; i++) {
    		scanf("%d%d", &s[i].x, &s[i].y);
    		if ((s[i].y < s[miny].y) || (s[i].y == s[miny].y && s[i].x < s[miny].x)) miny = i;
    	}
    	if (n == 2) {
    		printf("%d
    ", dis2(s[0], s[1]));
    		return 0;
    	}
    	std::swap(s[0], s[miny]);
    	O.x = s[0].x, O.y = s[0].y;
    	std::sort(s + 1, s + n);
    	v[tot++] = s[0], v[tot++] = s[1], v[tot++] = s[2];
    	for (int i = 3; i < n; i++) {
    		for (Point a = v[tot - 2], b = v[tot - 1]; tot > 2 && det(a, b, s[i]) <= 0; a = v[tot - 2], b = v[tot - 1]) tot--;
    		v[tot++] = s[i];
    	}
    	int now = 1;
    	for (int l = 0, r, D, tmp; l < tot; l++) {
    		r = (l + 1) % tot;
    		D = det(v[l], v[r], v[now]);
    		while (D < (tmp = det(v[l], v[r], v[(now + 1) % tot]))) D = tmp, now = (now + 1) % tot;
    		ans = std::max(ans, std::max(dis2(v[l], v[now]), dis2(v[r], v[now])));
    	}
    	printf("%d
    ", ans);
    	return 0;
    }
    

      

  • 相关阅读:
    前端启动摄像头的API
    落谷训练---
    树的遍历 (和) 玩转二叉树 的总结博客
    L2-010 排座位 (并查集)
    最长回文(manacher模板)
    L2-006 树的遍历
    面试题5:从尾到头打印链表
    面试题4:替换空格
    面试题3:二维数组中的查找
    poj 1511(spfa)
  • 原文地址:https://www.cnblogs.com/Memory-of-winter/p/10052532.html
Copyright © 2020-2023  润新知