您的位置:首页 > 其它

UVa 10088 (Pick定理) Trees on My Island

2015-03-26 14:38 501 查看
这种1A的感觉真好

#include <cstdio>
#include <vector>
#include <cmath>
using namespace std;
typedef long long LL;

struct Point
{
LL x, y;
Point(LL x=0, LL y=0):x(x), y(y) {}
};

Point operator - (const Point& A, const Point& B)
{ return Point(A.x-B.x, A.y-B.y); }

LL Cross(const Point& A, const Point& B)
{ return A.x*B.y-A.y*B.x; }

typedef vector<Point> Polygon;

LL Area(const Polygon& p)
{
LL ans = 0;
int n = p.size();
for(int i = 1; i < n-1; i++) ans += Cross(p[i]-p[0], p[i+1]-p[0]);
return abs(ans/2);
}

LL gcd(LL a, LL b) { return b == 0 ? a : gcd(b, a%b); }

LL Boundary(const Polygon& p)
{
LL ans = 0;
int n = p.size();
for(int i = 0; i < n-1; i++)
{
LL a = abs(p[i+1].x - p[i].x);
LL b = abs(p[i+1].y - p[i].y);
ans += gcd(a, b);
}
ans += abs(gcd(p[n-1].x-p[0].x, p[n-1].y-p[0].y));
return ans;
}

int main()
{
//freopen("in.txt", "r", stdin);
int n;
while(scanf("%d", &n) == 1 && n)
{
Polygon poly;
Point p;
for(int i = 0; i < n; i++)
{
scanf("%lld%lld", &p.x, &p.y);
poly.push_back(p);
}
LL A = Area(poly);
LL b = Boundary(poly);
printf("%lld\n", A - b/2 + 1);
}

return 0;
}


代码君

假设平面上有一个顶点均为格点的单纯多边形(simple polygon)

其面积为A,边界上的格点数为b,内部格点数为i,则有恒等关系:

A = b/2 + i - 1

链接:
http://episte.math.ntu.edu.tw/articles/sm/sm_25_10_1/page4.html
从问题的抛出,从特殊情况开始猜想,然后修正,最后给出证明。写得很好。

但是没有证明里面提到的“原子三角形”面积为1/2的命题,难道这个是非常显然的吗?=_=||

维基百科:
http://en.wikipedia.org/wiki/Pick%27s_theorem
比较严格的证明,但没有上一篇通俗易懂。
http://www.cut-the-knot.org/ctk/Farey.shtmlFarey%20Series
这个证明没看,但是后面提到了Pick定理在Farey级数中的应用,留坑,以后再看。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: