zoukankan      html  css  js  c++  java
  • CodeForces Goodbye2019 E.Divide Points (构造)

    题目:传送门

    思路及代码参考了这位大佬的博客 点此跳转

    现将点分为四类 :(0表示偶数,1表示奇数)

    1. (0,0)
    2. (1,1)
    3. (0,1)
    4. (1,0)

    如果有至少一个点属于 3或4 ,则可以将所有点分为 {1,2} 和 {3,4};
    这样划分,集合内部距离平方为偶,集合之间的距离平方为奇数,满足题意;

    如果没有点属于 3或4 ,则将所有点分为 {1} 和 {2} ;
    这样划分 1:( 2 * x,2 * y ) ; 2: ( 2 * z + 1,2 * k + 1 ) ;
    那么集合内部是 x1-x2 与 y1-y2 都是偶数
    集合之间 则都是奇数;
    平方和相加,集合内部的距离 为两个偶数之和
    平方和相加,集合之间的距离 为 两个奇数之和(奇数的平方还是奇数)
    故满足题意;

    如果所有点都是第一类的,那么我对所有坐标除以2,这样操作是对距离的相对关系是没有任何影响的,知道出现了非第一类点,就可以开始分类了(不存在奇数除以2的情况);

    因为我们是围绕第一类进行构造,为了保证一定会有第一类点,我们将所有坐标的进行平移,代码如下:

    #include<bits/stdc++.h>
    using namespace std;
    typedef long long LL;
    typedef pair<int,int> pii;
    typedef pair<LL,LL> pLL;
    const int N=1e6+5;
    const int inf=0x3f3f3f3f;
    const LL INF=1LL<<50;
    #define ls (i<<1)
    #define rs (i<<1|1)
    #define fi first
    #define se second
    #define mk make_pair
    #define pb push_back
    #define mem(a,b) memset(a,b,sizeof(a))
    #define debug puts("...")
    LL read()
    {
        LL x=0,t=1;
        char ch=getchar();
        while(!isdigit(ch)){ if(ch=='-')t=-1; ch=getchar(); }
        while(isdigit(ch)){ x=10*x+ch-'0'; ch=getchar(); }
        return x*t;
    }
    int x[N],y[N];
    vector<int> a,b;
    int main()
    {
        int n=read();
        for(int i=1;i<=n;i++)
            x[i]=read(),y[i]=read();
        for(int i=n;i;i--) x[i]-=x[1],y[i]-=y[1]; ///保证一定有(偶,偶)这一种情况
        while(1)
        {
            for(int i=1;i<=n;i++)
                if(x[i]%2||y[i]%2) goto out;
            for(int i=1;i<=n;i++)
                x[i]>>=1,y[i]>>=1;
        }out:;
        for(int i=1;i<=n;i++)
        {
            //printf("x=%d , y=%d
    ",x[i],y[i]);
            if(x[i]%2&&y[i]%2) b.pb(i);
            else if(x[i]%2==0&&y[i]%2==0) a.pb(i);
        }
        if(a.size()+b.size()==n)
        {
            printf("%d
    ",a.size());
            for(int i=0;i<a.size();i++)
                printf("%d ",a[i]);
        }
        else
        {
            printf("%d
    ",a.size()+b.size());
            for(int i=0;i<a.size();i++)
                printf("%d ",a[i]);
            for(int i=0;i<b.size();i++)
                printf("%d ",b[i]);
        }
        return 0;
    }
    
  • 相关阅读:
    poj3278 Catch That Cow
    poj2251 Dungeon Master
    poj1321 棋盘问题
    poj3083 Children of the Candy Cor
    jvm基础知识—垃圾回收机制
    jvm基础知识1
    java面试基础必备
    java soket通信总结 bio nio aio的区别和总结
    java scoket aIO 通信
    java scoket Blocking 阻塞IO socket通信四
  • 原文地址:https://www.cnblogs.com/DeepJay/p/12215030.html
Copyright © 2011-2022 走看看