zoukankan      html  css  js  c++  java
  • hdu2544

    这题可以这样来抽象:

     n对数,大小为1、2、3、...、n。现要求两个1之间有1个数,两个2之间有2个数,以此类推,两个n之间有n个数。并且,数的次序可以随意的。

    解决之道:

    准备知识:

    ①n对数,共2*n个数。所以要有2*n个位置来放置这2*n个数。

    ②sum()表示求和运算。

    正式解决:

    ①设k(k=1,2,..,n)放置的第一个位置ak,第二个位置bk。显然有bk-ak=k+1(假定下一个位置在上一个位置之前)。

    那么会有sum(bk-ak)=2+3+4+...+(n+1)=(1+2+3+...+n)+(1+1+...+1)=n*(n+1)/2+n。

    ②又因为要有2*n个位置来放置这2*n个数。则sum(ak+bk)=1+2+3+...+2*n=(1+2*n)*(2*n)/2=(1+2*n)*n。

    ③sum(ak+bk)=sum(ak+ak+k+1)=sum(2*ak+bk-ak)=2*sum(ak)+sum(bk-ak)=2*sum(ak)+n*(n+1)/2+n。

    ④比较②③可得:(1+2*n)*n=2*sum(ak)+n*(n+1)/2+n。可得sum(ak)=n*(3*n-1)/4。

    ⑤就像前面已经说过的一样,ak表示数k第一次出现的位置。ak不易确定。当可以肯定的是sum(ak)一定为正整数。

    那么就会有n=4*p或者3*n-1=4*p(p为正整数)。

    加一个大神的思路:

    补充:①+②------>n=4p或n+1=4p;
    ①-②------->n=4p或3n-1=4p
    3n-1=3(n+1)-4
    (3n-1)%4=(3(n+1))%4
    而(n+1)%4==0必有(3(n+1))%4==0
    所以条件取n%4==0||(n+1)%4==0更好

    两种代码:(都可以)

     1 # include<iostream>
     2 # include<cstdio>
     3 using namespace std;
     4 int main()
     5 {
     6     int n;
     7     while(scanf("%d",&n)&&n)
     8     {
     9         //if(n%4==0||(3*n - 1)%4==0)
    10         if(n%4==0||(n+1)%4==0)
    11        // printf("Y
    ");
    12        cout<<"Y"<<endl;
    13         else
    14         //printf("N
    ");
    15         cout<<"N"<<endl;
    16     }
    17     return 0;
    18 }
    View Code
  • 相关阅读:
    Codeforces 1265A Beautiful String
    1039 Course List for Student (25)
    1038 Recover the Smallest Number (30)
    1037 Magic Coupon (25)
    1024 Palindromic Number (25)
    1051 Pop Sequence (25)
    1019 General Palindromic Number (20)
    1031 Hello World for U (20)
    1012 The Best Rank (25)
    1011 World Cup Betting (20)
  • 原文地址:https://www.cnblogs.com/sxmcACM/p/3434174.html
Copyright © 2011-2022 走看看