[Usaco2010 OPen]Triangle Counting 数三角形
Time Limit: 10 Sec Memory Limit: 64 MB
Submit: 526 Solved: 262
[Submit][Status][Discuss]
Description
在一只大灰狼偷偷潜入Farmer Don的牛群被群牛发现后,贝西现在不得不履行着她站岗的职责。从她的守卫塔向下瞭望简直就是一件烦透了的事情。她决定做一些开发智力的小练习,防止她睡着了。想象牧场是一个X,Y平面的网格。她将N只奶牛标记为1…N (1 <= N <= 100,000),每只奶牛的坐标为X_i,Y_i (-100,000 <= X_i <= 100,000;-100,000 <= Y_i <= 100,000; 1 <= i <=N)。然后她脑海里想象着所有可能由奶牛构成的三角形。如果一个三角形完全包含了原点(0,0),那么她称这个三角形为“黄金三角形”。原点不会落在任何一对奶牛的连线上。另外,不会有奶牛在原点。给出奶牛的坐标,计算出有多少个“黄金三角形”。顺便解释一下样例,考虑五只牛,坐标分别为(-5,0), (0,2), (11,2), (-11,-6), (11,-5)。下图是由贝西视角所绘出的图示。
Input
第一行:一个整数: N 第2到第N+1行: 每行两个整数X_i,Y_i,表示每只牛的坐标
Output
* 第一行: 一行包括一个整数,表示“黄金三角形的数量”
Sample Input
5
-5 0
0 2
11 2
-11 -6
11 -5
-5 0
0 2
11 2
-11 -6
11 -5
Sample Output
5
HINT
题解:复杂度是极角排序的复杂度吧,双指针。
#include<cstring>
#include<cmath>
#include<iostream>
#include<algorithm>
#include<cstdio> #define ll long long
#define N 100007
using namespace std;
inline int read()
{
int x=,f=;char ch=getchar();
while(!isdigit(ch)){if(ch=='-')f=-;ch=getchar();}
while(isdigit(ch)){x=(x<<)+(x<<)+ch-'';ch=getchar();}
return x*f;
} int n;
ll ans;
struct Node
{
int x,y;
double angle;
friend inline bool operator<(Node x,Node y)
{
return x.angle<y.angle;
}
friend inline ll operator*(Node x,Node y)
{
return (ll)x.x*y.y-(ll)x.y*y.x;
}
}a[N]; void solve()
{
int r=,t=;
for (int i=;i<=n;i++)
{
while((r%n+)!=i&&a[i]*a[r%n+]>=) t++,r=r%n+;
ans+=(ll)t*(t-)/;
t--;
}
}
int main()
{
n=read();
for (int i=;i<=n;i++)
{
a[i].x=read(),a[i].y=read();
a[i].angle=atan2(a[i].y,a[i].x);
}
sort(a+,a+n+);
solve();
printf("%lld",(ll)n*(n-)*(n-)/-ans);
}
#undef N