比赛重现链接:2018新春大作战重现赛

出题人:

axuhognbo:徐红博
xuanhuang:秦圣昭
IceCapriccio:王炜良
JiaoGuan:陈海星

A:

提交链接

出题人:xuanhuang
AC:SUBMIT :65/180

百度一下我们可以知道:

幻方(Magic Square)是一种将数字安排在正方形格子中,使每行、列和对角线上的数字和都相等的方法。

幻方也是一种中国传统游戏。旧时在官府、学堂多见。它是将从一到若干个数的自然数排成纵横各为若干个数的正方形,使在同一行、同一列和同一对角线上的几个数的和都相等。

奇阶幻方
当n为奇数时,我们称幻方为奇阶幻方。可以用Merzirac法与loubere法实现,根据我的研究,发现用国际象棋之马步也可构造出更为神奇的奇幻方,故命名为horse法。

当然上面给出了直接的构造方法,下面给出一个构造幻方的模板链接:幻方构造

code1:
直接运用模板
code2:

    #include<bits/stdc++.h> 
    using namespace std;  
    int main()  
    {  
        int i,j,x1,y1,x2,y2,t,n;  
        cin>>t;  
        while(t--)  
        {  
            cin>>n;  
            int a[366][366]={0};//每组数据都要初始化二维数组 
            a[1][n/2+1]=1;//规律1 
            x1=1,y1=n/2+1;//x表示行,y表示列 
            for(i=2;i<=n*n;i++)//从2开始,上面1已经被放进了数组a[1][1] 
            {  
                x2=x1-1,y2=y1+1;//规律2 
                if((x2<1&&y2>n)||a[x2][y2]>0)//规律5 
                x2=x1+1,y2=y1;  
                else if(x2<1)//规律3 
                x2=n;  
                else if(y2>n)//规律4 
                y2=1;  
                a[x2][y2]=i;//将数放进数组 
                x1=x2,y1=y2;//更新变量,这里可以简化两对变量,使用一对变量x,y 
            }  
            for(i=1;i<=n;i++)  
            {  
                for(j=1;j<=n;j++)  
                {  
                    cout<<a[i][j];  
                    if(j<n)  
                    cout<<' ';  
                }  
                cout<<endl;  
            }  
        }  
        return 0;  
    }  

B:大牛的奇*技巧
提交链接: SDUTOJ-4154

出题人:axuhongbo
AC:SUBMIT : 106/296

点击链接,复制模板,稍微改动下输入输出即可

code1:

#include <stdio.h>
#include <stdlib.h>
int read()
{
    char ch=' ';
    int ans=0;
    while(ch<'0' || ch>'9')
        ch=getchar();
    while(ch<='9' && ch>='0')
    {
        ans=ans*10+ch-'0';
        ch=getchar();
    }
    return ans;
}
int main()
{
    int n,a,i,b;
    scanf("%d",&n);
    for(i = 0;i < n;i++)
    {
        a = read();
        if(i == n-2)
            b = a;
    }
    printf("%d\n",b);
    return 0;
}

code2:

#include <bits/stdc++.h>
using namespace std;

namespace FastIO{
    #define BUF_SIZE 10000000 /// 输入数据的大小.
    bool IOerror=0;
    inline char nc(){
        static char buf[BUF_SIZE], *p1=buf+BUF_SIZE, *pend=buf+BUF_SIZE;
        if(p1==pend){
            p1=buf;
            pend=buf+fread(buf, 1, BUF_SIZE, stdin);
            if(pend==p1){
                IOerror=1;
                return -1;
            }
        }
        return *p1++;
    }
    inline bool blank(char ch){
        return ch==' '||ch=='\n'||ch=='\r'||ch=='\t';
    }
    inline void read(int &x){
        char ch;
        int sign=1;
        while(blank(ch=nc()));
        if(IOerror)return;
        if(ch=='-'){
            sign=-1;
            ch=nc();
        }
        for(x=ch-'0'; (ch=nc())>='0'&&ch<='9'; x=x*10+ch-'0');
        x*=sign;
    }
    inline void read_ss(char *p){
        char ch;
        while(blank(ch=nc()));
        if(IOerror)return;
        for(int a=0; ; a++){
            if(ch==' '||ch=='\n'||ch=='\r'||ch==-1||ch=='\t'){
                *(p+a)=0;
                return;
            }
            *(p+a)=ch;
             ch=nc();
        }
    }
    #undef BUF_SIZE
}
using namespace FastIO;

int main() {
    int n;
    read(n);
    int maxn = -1e9 - 7;
    int minn = 1e9 + 7;
    int t;
    for (int i = 0; i < n; i++) {
        read(t);
        if(i==n-1-1) cout<<t;
    }
}

C:张起灵蛇宫寻宝

提交链接

出题人:axuhongbo
AC:SUBMIT : 40/97

首先根据题目中的提示,我们了解到本道题的加密方式,5栅栏加密 + rot5
以第一串数字为例:
首先写成
64073
59703 的形式,
然后根据rot5我们把这些数字都加上5
即19528
04258
根据栅栏密码我们只需要竖着把这些数字读出来即可:
即1094522588
同理我们解密出另外一层数字3148756193
根据题目中的提示企鹅,当然这两串数字就代表QQ号啦,
打开手机QQ搜索一下,你会在他们的空间里发现答案的秘密
code:

#include<stdio.h>
int main()
{
    printf("wudimeishaonv\n");
    return 0;
}

D:寻龙诀

提交链接

出题人:axuhongbo
AC:SUBMIT : 6/263

百度表白,第二条即是

百度传情——为TA写下心中情,生成密码传给TA,TA百度一下密码就懂你

我们可以自己先试一下这个怎么用,等你自己生成一条情书之后,你会发现,密码是 解蜜+一串数字的形式
这时候我们只需要把题目中的那一串文字对应成数字
百度搜索 解蜜15134828,即可得到

这是我们再用题目中蛇王的提示
解出对应数字:47713268,又得到

最后,继续搜索最后一串数字得到答案

(ps:只需把H题代码交上即可AC,感觉要被打)

E:真假美猴王

提交链接

出题人:axuhongbo
AC:SUBMIT : 178/373

水题,本来只要大家扫完三个二维码就可以了解真相(ps:你扫了又不一定真付钱,付款的时候不是还要输密码吗),好多人看到第三个数目特别大,于是就不敢扫了。其实扫完第三个你就会发现其实,第三个并不是付款二维码,而是一个网址链接,提示你文中的十个黑体词是支付口令,打开支付宝,搜索红包,输入这十个中的一个领取红包即可获得要输出的答案。

code:

#include<stdio.h>
#include<string.h>
#include<math.h>

int main()
{
    printf("gouniandaji\n");
    return 0;
}

F:雪域羚羊的来访

提交链接

出题人:axuhongbo
AC:SUBMIT : 31/86

如果按照原始方法去写,从L~R对2~ n进行计算,如果因子数为奇数那么该光源就是关闭的,因为是从2开始计算的,而1是所有数的一个因子,所以因子数为奇数的都关闭了。这种方法结果很明显,超时。然后看了网上的讨论。得知因子数为奇数的数叫做完全平方数,完全平方数就是能够写成m*m的形式的数,它其中一个特点就是因子数是奇数个。但是数据是10的15次方,如果一个个判断还是超时,怎么办呢?声明一个变量 i 从 L 的算术平方根开始枚举,直到 i*i 大于R。只要i*i在[L,R]范围内,那么说明编号为 i*i 的光源是关闭的。定义sum=R-L+1,表示区间内光源总数,每当光源是关闭的就减一。
code:

#include<stdio.h>
#include<stdlib.h>
#include<math.h>
int main()
{
    int n;
    long long a,b,len=0;//因为数据比较大,定义为long long 型 
    scanf("%lld%lld%lld",&n,&a,&b);
    long long sum;
    sum=b-a+1;//区间中光源总数 
    for(long long i=sqrt(a);i*i<=b;i++)
    {
            if(i*i>=a&&i*i<=b)
            {
                sum--;//关闭的光源减去 
            }
    } 
    printf("%lld\n",sum); 
    return 0;
}

G:黑小虎的执念

提交链接

出题人:IceCapriccio
AC:SUBMIT : 1/4

  1. 题目中说只能输入 0 - 255 之间的数以及题目的提示,考虑是汉字编码每一字节的值
  2. 你需要知道 GBK 编码每个汉字对应 2 个字节,UTF-8 编码每个汉字对应 3 个字节。
  3. 题目给的一首诗,每首诗都有 9 个字。
  4. 题目说需要输入 18 个 0 - 255 的数,考虑是 GBK 编码。
  5. 具体是哪一句的 GBK 编码?需要自己尝试,诗一共有 4 句不同的诗句,最多需要尝试 4 次可以得到 AC 。

答案是第二句的 GBK 编码:203 181 202 199 193 201 212 182 181 196 186 163 181 196 207 224 203 188
code:

#include <stdio.h>
#include <stdlib.h>
int main()
{
    printf("203 181 202 199 193 201 212 182 181 196 186 163 181 196 207 224 203 188\n");
    return 0;
}

H:

提交链接

出题人:axuhongbo
AC:SUBMIT : 35/51

这是一道典型的数学问题。做题前首先要做出计算公式,找到公式后写程序就简单了。要想得到A太太所得的钱数,因为要考虑到浮点数为问题,根据计算得到公式
三人都做每人应做的天数s=(x+y)/3.0;A多做的天数a=x-s;B多做的天数b=y-s;C应该付给A的钱数pay=a/(a+b)*z。

#include<cstdio>
#include<iostream>
using namespace std;

int T[20];
int y[10];
int z[1000];

int main ()
{
    int T;
    scanf("%d",&T);
    while(T--)
    {
    int x,y,z;
    double a,b,s,pay;


    scanf("%d%d%d",&x,&y,&z);

        s=(x+y)/3.0;      //三人都做每人应做的天数
        a=x-s;            //A多做的天数
        b=y-s;            //B多做的天数 
        pay=a/(a+b)*z;    //C应付给A的钱数
        int k=pay+0.5;    //将钱数四舍五入得到整数
        cout<<k<<endl;
    }
    return 0;

}

I: 玉兔小仙女奇遇记

提交链接

出题人:JiaoGuan
AC:SUBMIT : 1/9

这道题其实很简单,实际就是给出N个点的坐标
和中心点的坐标及其半径,判断多少少个点在中心点的半径范围内,
同时更新一下离中心点最近的距离
(当没有点在半径范围内需要用这个距离减去半径输出)
关于题意的解释,“小仙女”在N个点之间的路线虽然不是直线,但是这N个点
都是端点/终点,即“小仙女”一定会路过这N个点。
故题目就简化为判断N个点中,有多少个点到中心点的距离 <= R,
若存在这样的点,按照题目要求输出即可
若不存在,则输出N个点中到中心点的距离最近的距离再减半径
(因为一旦“小仙女”进入JiaoGuan视线半径后。。。)
另外当N个点中,存在点与中心点重合,则也是根据题目要求输出:
“Just stay and 999”,没错是要祝999滴,毕竟出题人是JiaoGuan本人

code:


#include <stdio.h>
#include <stdlib.h>
#include <math.h>
double dis(int a, int b, int x, int y); //求两点距离
int main()
{
    int a, b, r;
    while(scanf("%d %d %d", &a, &b, &r) != EOF)
    {
        int i, n, num = 0;
        int x, y;
        double m = 200000;
        scanf("%d", &n);
        int flag = 0;
        for(i = 1; i <= n; i++)
        {
            scanf("%d %d", &x, &y);
            if(x == a&&y == b)  //存在点与中心点重合
            {
                flag = 1;
            }
            double len = dis(a, b, x, y);
            if(len <= r * 1.0)  //点在半径范围内
            {
                num++;
            }
            else
            {
                len -= r * 1.0;  //JjaoGuan会去接“小仙女”
                if(len < m)  //更新最短距离
                {
                    m = len;
                }
            }
        }
        if(flag == 1)
        {
            printf("Just stay and 999\n");  //告诉JiaoGuan不要动+祝999
            continue;
        }
        if(num == n)
        {
            printf("Congratulation on JiaoGuan\n");
            printf("Fairy: Emmmm\n");
            continue;
        }
        if(num > 0)
        {
            printf("JiaoGuan will meet fairy %d time", num);
            if(num > 1)
            {
                printf("s");
            }
            printf("\n");
            continue;
        }
        else
        {
            printf("minlen = %.2f\n", m);
            continue;
        }
    }

    return 0;
}
double dis(int a, int b, int x, int y)
{
    return sqrt((a - x) * (a - x) + (b - y) * (b - y));
}

J - 金鸡报晓

提交链接

出题人:IceCapriccio
AC:SUBMIT : 109 /119

事实证明,有很多人在翻到这张图片中部的时候就已经失去了耐心,如果你从底部开始往上看或者足够耐心的话,你会发现在这张图片的底部有一句:

事实上,如果不是本题目在放出的时候忘记把样例丢出来的话,可能大家做的并不能这么顺利,尽管如此,还是有一部分小伙伴不能一次AC。

***红猪小妹

提交链接

出题人:axuhongbo
AC:SUBMIT : 20/167

事实上,本题并没有想象中的那么难,题目中只说了两个数相加,那么在int过不去之后,你把数据类型尝试下double即可AC,顶多再试一下long long ,并不需要用到大数。至于保留几位小数的问题,由于是特判题,所以保证了无论你保留几位小数都可以AC。

#include <stdio.h>
int main(void)
{
    double a,b,sum;
    while(scanf("%lf%lf",&a,&b)!=EOF)
    {
        sum=a+b;
        printf("%lf\n",sum);
    }
    return 0;
}

L - 521 ACM 来自一只单身狗的表白

提交链接

出题人:axuhongbo
AC:SUBMIT : 20/66

本道题目道出了题目顺序的奥秘,事实上如果你经历了寻龙诀这道题目的历练,这道题很好求,只需写出题目对应的整数序列,然后求一下逆序数对数,在进行一下乘方取模即可。(ps:看下本题的模数,有没有发现什么问题呢?)

#include <bits/stdc++.h> //万能头文件
using namespace std;

int main()
{
long long n=pow(14,14);
n=n%1667642815;
printf("%lld\n",n);
    return 0;
}

ps:本套题其实还有藏头彩蛋