zoukankan      html  css  js  c++  java
  • codeforces 849B

    codeforces 849B

    B. Tell Your World

    introduction

    判断是否存在两条线,使得所有的点都落在这两条线上,并且每条线上至少有一个点

    method

    先取三个点,两两之间连线,则如果满足要求,三条线必有一条是结果中的直线。剩下的工作就是判断剩下的点是否在这条直线上,或者到直线的距离与第三个点到直线的距离相等,并且在同侧

    useful knowledge

    • 判断两个浮点数是否相等的方法是,将两个浮点数做差取绝对值,与预设的精度比较,例如

      eps=1e-7
      fabs(a-b)>1e-7

      如果为True,那么a大于b
      为什么要这么做?

    • 直线表达成乘法的形式,可以避免引入浮点数

    tips

    • 只有在求点线距离的时候使用浮点数,其余时候使用long long
    • 使用浮点数有很多问题,在可以使用整数的情况下优先使用整数

    AC code

    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #include<string>
    #include<vector>
    #include<cmath>
    #include<cassert>
    #define DEBUG(x) cout<<#x<<" = "<<x<<endl
    typedef long long ll;
    using namespace std;
    const int MAXN=1e3+10;
    const double eps=1e-7;
    int n;
    ll ycod[MAXN];
    struct line{
        ll A,B,C;
        line(){}
        line(ll x1,ll y1,ll x2,ll y2)
        {
            A=(y1-y2);
            B=-(x1-x2);
            C=y1*(x1-x2)-(y1-y2)*x1;
        }
        double dist(ll x,ll y)
        {
            return fabs(A*x+B*y+C)*1.0/(sqrt(A*A*1.0+B*B*1.0));
        }
        bool online(ll x,ll y)
        {
            return (A*x+B*y+C)==0;
        }
        bool sameside(ll x1,ll y1,ll x2,ll y2)
        {
            ll r1=A*x1+B*y1+C,
            r2=A*x2+B*y2+C;
            bool rt= (r1>0&&r2>0)||(r1<0&&r2<0);
    //        if(n==20)assert(rt==true);
            return rt;
        }
    };
    bool judge(line &l,ll idx)
    {
        double d=l.dist(idx,ycod[idx]);
        for(int i=4;i<=n ;i++ ){
            if(l.online(i,ycod[i]))continue;
            if(!l.sameside(idx,ycod[idx],i,ycod[i]))return false;
            double td=l.dist(i,ycod[i]);
            if(fabs(td-d)>eps)return false;
        }
        return true;
    }
    int main()
    {
    //    freopen("in.txt","r",stdin);
        cin>>n;
        for(int i=1;i<=n ;i++ ){
            cin>>ycod[i];
        }
        bool ok;
        if(n==3){
            line l1=line(1,ycod[1],2,ycod[2]);
            ok =!l1.online(3,ycod[3]);
        }
        else {
            line l1=line(1,ycod[1],2,ycod[2]);
            line l2=line(2,ycod[2],3,ycod[3]);
            line l3=line(1,ycod[1],3,ycod[3]);
            if(l1.online(3,ycod[3])==false)
                ok =judge(l1,3)||judge(l2,1)||judge(l3,2);
            else {
                double d=-1;
                int idx=-1;
                ok=true;
                for(ll i=4;i<=n ;i++ ){
                    if(l1.online(i,ycod[i]))continue;
                    int td=l1.dist(i,ycod[i]);
                    if(d==-1)d=td,idx=i;
                    else {
                        if(l1.sameside(idx,ycod[idx],i,ycod[i])==false){
                                ok=false;
                                break;
                        }
                        else if(abs(d-td)>eps){
                                ok=false;
                                break;
                        }
                    }
                }
                if(idx==-1)ok=false;
            }
        }
        if(ok)cout<<"Yes"<<endl;
        else cout<<"No"<<endl;
    }
    
    
  • 相关阅读:
    软件工程(2018)第一次作业
    SQA计划
    再冲刺
    第三次冲刺
    第二次冲刺
    小组第一次冲刺
    团队合作初体验
    关于git的认识与想法
    我的第一篇博客
    SQA计划和系统测试规程
  • 原文地址:https://www.cnblogs.com/MalcolmMeng/p/10141891.html
Copyright © 2011-2022 走看看