codeforces 850 A

codeforces 850 A

A. Five Dimensional Points

introduction

n个点中,是否存在一个点,与另外任意两个点连成的向量,为锐角

method

首先在2维的空间中,要让角不为锐角,最多只能存在5个点(四个向量) 。鸽巢原理。在k维空间中,最多只能存在2k+1个节点。k=5时,最多只能存在11个节点。所以:

  • 输出0,如果节点数大于11
  • 枚举,如果节点数小于等于10

tips

  1. 成角的向量不能随意交换向量的两个端点
  2. 节点数=向量数+ 1
  3. 鸽巢原理是非常有用

reference

http://codeforces.com/blog/entry/54317
https://blog.csdn.net/Fusheng_Yizhao/article/details/78557741
鸽笼原理 谢聪智

code

#include<cstdio>
#include<cstdlib>
#include<cstring>
#include<iostream>
#include<algorithm>
#include<string>
#include<vector>
#include<cmath>
#include<map>
#include<istream>
#include<ostream>
#define DEBUG(x) cout<<#x<<" = "<<x<<endl
#define pi acos(-1)
using namespace std;
const int MAXN=1e3+10;
struct point{
    int a[5];
    point(){memset(a,0,sizeof(a));}
    friend istream & operator>>(istream &in,point &p)
    {
        for(int i=0;i<5 ;i++ ){
            in>>p.a[i];
        }
        return in;
    }
    friend ostream &operator<<(ostream &out,const point &p)
    {
        for(int i=0;i<5 ;i++ ){
            out<<p.a[i]<<" ";
        }
        return out;
    }
};
typedef point vec;
inline vec mkvec(point &p1,point &p2)
{
    vec v;
    for(int i=0;i<5 ;i++ ){
        v.a[i]=p2.a[i]-p1.a[i];
    }
    return v;
}
int n;
point pts[MAXN];
int dot(vec &p1,vec &p2)
{
    int rt=0;
    for(int i=0;i<5 ;i++ ){
        rt+=p1.a[i]*p2.a[i];
    }
    return rt;
}
///根据鸽巢原理可以大幅度降低复杂度
///向量是有方向的
int main()
{
//    freopen("in.txt","r",stdin);
    cin>>n;
    for(int i=1;i<=n ;i++ ){
        cin>>pts[i];
    }
    vector<int>ans;
    if(n<3){
        for(int i=1;i<=n ;i++ ){
            ans.push_back(i);
        }
    }
    else if(n<=11)
    for(int i=1;i<=n ;i++ ){
        vector<vec>v;
        for(int j=1;j<=n ;j++ ){
            if(i!=j)
            v.push_back(mkvec(pts[i],pts[j]));
        }
        bool ok=true;
        for(int k=0;k<v.size() ;k++ ){
            for(int u=k+1;u<v.size() ;u++ ){
                if(dot(v[k],v[u])>0)ok=false;
            }
        }
        if(ok)ans.push_back(i);
    }
    cout<<ans.size()<<endl;
    for(int i=0;i<ans.size() ;i++ ){
        cout<<ans[i]<<endl;
    }
}
原文地址:https://www.cnblogs.com/MalcolmMeng/p/10195067.html