JZOJ3493 三角形

Description

  平面上有n个点,求出用这些点可以构成的三角形数。

Input

  第一行一个整数n。

  接下来n行,每行两个整数,表示点的坐标。

Output

  输出仅一个整数,表示所求答案。

Sample Input

  5
  0 0
  1 1
  1 -1
  -1 -1
  -1 1

Sample Output

  8

Data Constraint

  对于50%的数据,n<=300。

  对于100%的数据,n<=3000,坐标的绝对值不超过10^4,保证没有重合的点。
 

Solution

  枚举第一个点,对于剩下的点按照和这个点连线的斜率排序一下,把相同斜率的线段放在一起,可以算出选到两条相同斜率的线段方案数,即不能构成三角形的方案数,然后统计答案。注意处理斜率不存在的情况。

 1 #pragma GCC optimize(2)
 2 #include<cstdio>
 3 #include<algorithm>
 4 using namespace std;
 5 int l,n,a[4000],b[4000],sum,r;
 6 long long ans;
 7 double d[9500000];
 8 int main()
 9 {
10     scanf("%d",&n);
11     for (int i=1;i<=n;i++)
12         scanf("%d%d",&a[i],&b[i]);
13     ans=(n*(n-1))/2;
14     ans=(ans*(n-2))/3;
15     for (int i=1;i<=n-1;i++)
16     {
17         l=0;r=0;
18         for (int j=i+1;j<=n;j++)
19             if (a[j]-a[i]==0) 
20                 r++;
21             else
22                 d[++l]=(double(b[j]-b[i]))/(double(a[j]-a[i]));
23         sort(d+1,d+l+1);
24         sum=1;
25         for (int j=2;j<=l;j++)
26             if (d[j]==d[j-1])
27                 sum++;
28             else
29             {
30                 ans=ans-((sum*(sum-1))/2);
31                 sum=1;
32             }
33         ans=ans-((sum*(sum-1))/2);
34         ans=ans-(r*(r-1))/2;
35     }
36     printf("%lld",ans);
37 }
View Code

 

posted @ 2018-08-06 21:12  kasiruto  阅读(165)  评论(0编辑  收藏  举报