试题A:组队
本题总分:5分
作为篮球队教练,你需要从以下名单中选出 1 号位至 5 号位各一名球员, 组成球队的首发阵容。
每位球员担任 1 号位至 5 号位时的评分如下表所示。请你计算首发阵容 1 号位至 5 号位的评分之和最大可能是多少?
解题思路:
这道题就是取某个位置中分数最高的队员,当然要注意一个队员只能在一个位置,不能同时占多个位置。
答案:
490
试题B:年号字串
本题总分:5分
小明用字母 A 对应数字 1,B 对应 2,以此类推,用 Z 对应 26。对于 27 以上的数字,小明用两位或更长位的字符串来对应,例如 AA 对应 27,AB 对 应 28,AZ 对应 52,LQ 对应 329。 请问 2019 对应的字符串是什么?
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一 个大写英文字符串,在提交答案时只填写这个字符串,注意全部大写,填写多 余的内容将无法得分。
解题思路:
这道题就是一个26进制的问题,例如329,先除以26,得到的是12,余数是17,那么17对应的是字母Q,接下来再用12除以26,得到的是0,余数是12,而12对应的字母是L,所以答案就是LQ。要逆序表示,所以我用递归来实现!!!
程序代码:
#include<stdio.h>
void solve(int n)
{
if(!n)
return ;
solve(n/26);
printf("%c",(char)(n%26+64));
}
int main()
{
solve(2019);
return 0;
}
答案:
BYQ
试题C:数列求值
本题总分:10分
给定数列 1, 1, 1, 3, 5, 9, 17, …,从第 4 项开始,每项都是前 3 项的和。求 第 20190324 项的最后 4 位数字。
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一 个 4 位整数(提示:答案的千位不为 0),在提交答案时只填写这个整数,填写 多余的内容将无法得分。
解题思路:
类似于斐波那契额数列的规律,因为题中说要得到最后四位数字,所以将结果对10000求余即可!!!
程序代码:
#include<stdio.h>
int a[20190325];
int main()
{
a[1]=1;
a[2]=1;
a[3]=1;
for(int i=4;i<=20190324;i++)
{
a[i]=(a[i-1]+a[i-2]+a[i-3])%10000;
}
printf("%d\n",a[20190324]);
return 0;
}
答案:
4659
试题D:数的分解
本题总分:10分
把 2019 分解成 3 个各不相同的正整数之和,并且要求每个正整数都不包 含数字 2 和 4,一共有多少种不同的分解方法? 注意交换 3 个整数的顺序被视为同一种方法,例如 1000+1001+18 和 1001+1000+18 被视为同一种。
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一 个整数,在提交答案时只填写这个整数,填写多余的内容将无法得分。
解题思路:
这道题我想的就是纯暴力解题,三个数各不相同,最少为一位数,最多为四位数,然后依次使得i,j,k的个十百千位不等于2和4就可以了,但是由于题中说的交换三个整数的顺序被视为同一种方法,而三个整数一共有3!=6种情况,所以我们要对最后的结果除以6才是正确的!!!
程序代码:
#include<stdio.h>
int main()
{
int ans=0;
for(int i=1;i<2019;i++)
{
for(int j=1;j<2019;j++)
{
for(int k=1;k<2019;k++)
{
if(i+j+k==2019&&i%10!=2&&i%10!=4&&(i/10)%10!=2&&
(i/10)%10!=4&&(i/100)%10!=2&&(i/100)%10!=4&&
(i/1000)%10!=2&&(i/1000)%10!=4&&j%10!=2&&j%10!=4&&(j/10)%10!=2&&
(j/10)%10!=4&&(j/100)%10!=2&&(j/100)%10!=4&&
(j/1000)%10!=2&&(j/1000)%10!=4&&k%10!=2&&k%10!=4&&(k/10)%10!=2&&
(k/10)%10!=4&&(k/100)%10!=2&&(k/100)%10!=4&&
(k/1000)%10!=2&&(k/1000)%10!=4&&i!=j&&i!=k&&j!=k)
ans++;
}
}
}
printf("%d\n",ans/6);
return 0;
}
答案:
40785
试题E:迷宫
本题总分:15分
下图给出了一个迷宫的平面图,其中标记为 1 的为障碍,标记为 0 的为可 以通行的地方。
010000 000100 001001 110000
迷宫的入口为左上角,出口为右下角,在迷宫中,只能从一个位置走到这 个它的上、下、左、右四个方向之一。 对于上面的迷宫,从入口开始,可以按DRRURRDDDR 的顺序通过迷宫, 一共 10 步。其中 D、U、L、R 分别表示向下、向上、向左、向右走。 对于下面这个更复杂的迷宫(30 行 50 列),请找出一种通过迷宫的方式, 其使用的步数最少,在步数最少的前提下,请找出字典序最小的一个作为答案。 请注意在字典序中D<L<R<U。(如果你把以下文字复制到文本文件中,请务 必检查复制的内容是否与文档中的一致。在试题目录下有一个文件 maze.txt, 内容与下面的文本相同)
01010101001011001001010110010110100100001000101010 00001000100000101010010000100000001001100110100101 01111011010010001000001101001011100011000000010000 01000000001010100011010000101000001010101011001011 00011111000000101000010010100010100000101100000000 11001000110101000010101100011010011010101011110111 0001101101010100100100101000000100010100111000000010100000101000100110101010111110011000010000111010 00111000001010100001100010000001000101001100001001 11000110100001110010001001010101010101010001101000 00010000100100000101001010101110100010101010000101 11100100101001001000010000010101010100100100010100 00000010000000101011001111010001100000101010100011 10101010011100001000011000010110011110110100001000 10101010100001101010100101000010100000111011101001 10000000101100010000101100101101001011100000000100 10101001000000010100100001000100000100011110101001 00101001010101101001010100011010101101110000110101 11001010000100001100000010100101000001000111000010 00001000110000110101101000000100101001001000011101 10100101000101000000001110110010110101101010100001 00101000010000110101010000100010001001000100010101 10100001000110010001000010101001010101011111010010 00000100101000000110010100101001000001000000000010 11010000001001110111001001000011101001011011101000 00000110100010001000100000001000011101000000110011 10101000101000100010001111100010101001010000001000 10000010100101001010110000000100101010001011101000 00111100001000010000000110111000000001000000001011 10000001100111010111010001000110111010101101111000
这是一道结果填空的题,你只需要算出结果后提交即可。本题的结果为一 个字符串,包含四种字母 D、U、L、R,在提交答案时只填写这个字符串,填 写多余的内容将无法得分。
解题思路:
看到这种题,我们就应该想到DFS和BFS了,搜索遍历,遍历的时候按照字典序从小到大的顺序进行四个方向遍历进行了。
程序代码:
#include<stdio.h>
#include<string.h>
#define N 30
#define M 50
struct node
{
int x;
int y;
int s;//路程
int f;//上一个位置下标
char ch;//上一个走向
};
node que[N*M];
int map[N][M]=
{
0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0,
0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 1, 0, 0, 1, 0, 1,
0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0,
0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1,
0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0,
1, 1, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1,
0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0,
1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0,
0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 1,
1, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0,
0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1,
1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0,
0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1,
1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 1, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0,
1, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 1,
1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0,
1, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 0, 1,
0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1,
1, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0,
0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1,
1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1,
0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1,
1, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 0,
0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0,
1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0,
0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1,
1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0,
1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0,
0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1,
1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 1, 1, 0, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 1, 1, 0, 0, 0
};
int book[N][M],head,tail;
int next1[4][2]=
{//按照字典序
{1,0},//下 Down
{0,-1},//左 Left
{0,1},//右 Right
{-1,0}//上 Up
};
void print(int ans)
{
if(!ans)
return ;
print(que[ans].f);
printf("%c",que[ans].ch);
}
void bfs()
{
que[tail].x=0;
que[tail].y=0;
que[tail].s=0;
que[tail].f=0;
que[tail++].ch=0;
book[0][0]=1;
int flag=0;
while(head<tail)
{
int tx,ty;
for(int i=0;i<4;i++)
{
tx=que[head].x+next1[i][0];
ty=que[head].y+next1[i][1];
if(tx<0||tx>=N||ty<0||ty>=M)
continue;
if(map[tx][ty]==0&&book[tx][ty]==0)
{
book[tx][ty]=1;
que[tail].x=tx;
que[tail].y=ty;
que[tail].s=que[head].s+1;
que[tail].f=head;
if(next1[i][0])
{
que[tail].ch=(next1[i][0]==1 ? 'D':'U');
}
else if(next1[i][1])
{
que[tail].ch=(next1[i][1]==1 ? 'R':'L');
}
tail++;
if(tx==N-1&&ty==M-1)
{
flag=1;
break;
}
}
}
if(flag==1)
break;
head++;
}
print(tail-1);
}
int main()
{
bfs();
return 0;
}
答案:
DDDDRRURRRRRRDRRRRDDDLDDRDDDDDDDDDDDDRDDRRRURRUURRDDDDRDRRRRRRDRRURRDDDRRRRUURUUUUUUULULLUUUURRRRUULLLUUUULLUUULUURRURRURURRRDDRRRRRDDRRDDLLLDDRRDDRDDLDDDLLDDLLLDLDDDLDDRRRRRRRRRDDDDDDRR
试题F:特别数的和
时间限制: 1.0s 内存限制: 256.0MB 本题总分:15 分
【问题描述】 小明对数位中含有 2、0、1、9 的数字很感兴趣(不包括前导 0),在 1 到 40 中这样的数包括 1、2、9、10 至 32、39 和 40,共 28 个,他们的和是 574。 请问,在 1 到 n 中,所有这样的数的和是多少?
【输入格式】
输入一行包含两个整数 n。
【输出格式】
输出一行,包含一个整数,表示满足条件的数的和。
【样例输入】 40
【样例输出】 574
【评测用例规模与约定】 对于 20% 的评测用例,1≤n≤10。 对于 50% 的评测用例,1≤n≤100。 对于 80% 的评测用例,1≤n≤1000。 对于所有评测用例,1≤n≤10000。
解题思路:
这道题主要就是找出在一定范围内数位中出现 2、0、1、9 这四个数字之一的所有数字,既然这样那就直接暴力吧!!!
程序代码:
#include<iostream>
#include<cstdio>
using namespace std;
int main()
{
int n,num=0;
cin>>n;
for(int i=1;i<=n;i++)
{
int x=i;
while(x)
{
if(x%10==2||x%10==0||x%10==1||x%10==9)
{
num+=i;
break;
}
x/=10;
}
}
cout<<num<<endl;
return 0;
}
试题G:完全二叉树的权值
时间限制: 1.0s 内存限制: 256.0MB 本题总分:20 分
【问题描述】 给定一棵包含 N 个节点的完全二叉树,树上每个节点都有一个权值,按从 上到下、从左到右的顺序依次是 A1, A2, ··· AN,如下图所示:
现在小明要把相同深度的节点的权值加在一起,他想知道哪个深度的节点 权值之和最大?如果有多个深度的权值和同为最大,请你输出其中最小的深度。 注:根的深度是 1。
【输入格式】
第一行包含一个整数 N。 第二行包含 N 个整数 A1, A2, ··· AN 。
【输出格式】
输出一个整数代表答案。
【样例输入】 7 1 6 5 4 3 2 1【样例输出】 2
【评测用例规模与约定】 对于所有评测用例,1≤ N ≤100000,−100000≤ Ai ≤100000。
解题思路:
这道题如果学过完全二叉树的性质就不难了,完全二叉树的第 i 层的最大节点数为 2^(i-1) 个,那么对于某个下标的元素,我们只需要知道它属于哪一层就行了,因为题中所求的是相同深度的节点的权值,节点的数据范围N最大为100000,而具有n个节点的完全二叉树的深度公式为:向下取整(log2(n))+1,也就是向下取整(log2(100000))+1=17,又因为题中所说根的深度为1,所以此完全二叉树的深度应该为17+1=18层,下面我们来看代码吧,必要的注释已在其中标注!!!
程序代码:
#include<iostream>
#include<cstdio>
using namespace std;
#define MAX 18//二叉树的最大层数
long long a[MAX];
int deep(int x)//获取下标为x的节点的深度
{
int ans=0;
while(x>0)
{
x/=2;//代表同一层
ans++;
}
return ans;
}
int main()
{
int n,t;
cin>>n;
for(int i=1;i<=n;i++)
{
scanf("%d",&t);
a[deep(i)]+=t;//树的同一层节点权值相加
}
int res=-99999999,tree;
for(int i=1;i<=MAX;i++)
{
if(a[i]>res)//比较
{
res=a[i];//更新
tree=i;//深度i赋值给变量tree
}
}
cout<<tree<<endl;
return 0;
}
试题H:等差数列
时间限制: 1.0s 内存限制: 256.0MB 本题总分:20 分
【问题描述】
数学老师给小明出了一道等差数列求和的题目。但是粗心的小明忘记了一 部分的数列,只记得其中 N 个整数。 现在给出这 N 个整数,小明想知道包含这 N 个整数的最短的等差数列有 几项?
【输入格式】
输入的第一行包含一个整数 N。 第二行包含 N 个整数 A1,A2,··· ,AN。(注意 A1 ∼ AN 并不一定是按等差数 列中的顺序给出)
【输出格式】
输出一个整数表示答案。
【样例输入】 5 2 6 4 10 20
【样例输出】 10
【样例说明】 包含 2、6、4、10、20 的最短的等差数列是 2、4、6、8、10、12、14、16、 18、20。
【评测用例规模与约定】 对于所有评测用例,2≤ N ≤100000,0≤ Ai ≤109。
解题思路:
这道题首先应该考虑公差等不等于0的情况,公差不为0的时候,我们先所给数组序列排序之后,求出相邻数字差值的最大公约数,最终得到的就是公差;公差为0的时候,不用多想,最少就是n项。
程序代码:
#include<iostream>
#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
int a[100001];
int gcd(int a,int b)
{
int r;
while(b!=0)
{
r=a%b;
a=b;
b=r;
}
return a;
}
int main()
{
int n,d;
int maxn=0,minn=0x3f3f3f;
cin>>n;
for(int i=0;i<n;i++)
{
cin>>a[i];
maxn=max(maxn,a[i]);
minn=min(minn,a[i]);
}
sort(a,a+n);
d=a[1]-a[0];
for(int i=2;i<n;i++)
d=gcd(d,a[i]-a[i-1]);
if(d==0)
cout<<n<<endl;
else
cout<<((maxn-minn)/d+1)<<endl;
return 0;
}
试题I:后缀表达式
时间限制: 1.0s 内存限制: 256.0MB 本题总分:25 分
【问题描述】 给定 N 个加号、M 个减号以及 N + M + 1 个整数 A1,A2,··· ,AN+M+1,小 明想知道在所有由这 N 个加号、M 个减号以及 N + M +1 个整数凑出的合法的 后缀表达式中,结果最大的是哪一个?
请你输出这个最大的结果。 例如使用1 2 3 + -,则 “2 3 + 1 -” 这个后缀表达式结果是 4,是最大的。
【输入格式】
第一行包含两个整数 N 和 M。 第二行包含 N + M + 1 个整数 A1,A2,··· ,AN+M+1。
【输出格式】
输出一个整数,代表答案。
【样例输入】 1 1 1 2 3
【样例输出】 4
【评测用例规模与约定】 对于所有评测用例,0≤ N,M ≤100000,−109 ≤ Ai ≤109。
解题思路:
这道题一开始有点懵,还是被后缀表达式这个概念整懵了,从概念上讲,后缀表达式的意义和中缀表达式应该是一样的,想想我们熟悉的中缀表达式,我们可以自由定制数字运算的顺序,那么后缀表达式也应该有这种能力,即能随意组合运算顺序,我们知道这个概念就行。第二点是如果只有 + 、- 运算符,那么所有的数字都可以看成是相加的,-运算符可以看成负号。那么题目就可以看成有 N + M + 1 个数字进行相加,但是必须要有 M 个数字变成其本身的相反数,我们很容易想到可以把负数变成它的相反数,就成了正数,顺序应该是先将绝对值最大的负数变成正数,再是其他的数字。我们还需要讨论负数的个数和 M 的关系:1、给定的数字本身中负数的个数小于 M,这种情况下剩下绝对值最小的几个负数。2、给定的数字本身中负数的个数大于 M, 这种情况和 1 相似。3、给定的数字本身中负数的个数等于 M,这种情况全是正数,最后做加法就行了。
程序代码:
#include<iostream>
#include<cstdio>
#include<cmath>
#include<algorithm>
using namespace std;
#define MAXN 200001
int num[MAXN];
int cmp(int a,int b)
{
return abs(a)>abs(b);//按绝对值从大到小排序
}
int main()
{
int N,M;
cin>>N>>M;
int n=N+M+1;
long long ans=0;
for(int i=0;i<n;i++)
cin>>num[i];
sort(num,num+n,cmp);
for(int i=0;i<n&&M>0;i++)
{
if(num[i]<0)
{//将负数变成正数
num[i]=-num[i];
M--;
}
}
if(M)//如果还存在负号,则将最后的数字变成负数
{
for(int i=n-M;i<n;i++)
num[i]=-num[i];
}
for(int i=0;i<n;i++)
ans+=num[i];
cout<<ans<<endl;
return 0;
}
附:好了,暂时就写到这里吧,最后一题不太明白就不写了,总的来说,当时坐在考场的我还是有些紧张的,毕竟这是我第一次参加蓝桥杯,而且有些题看似简单,实则带有坑。。。继续努力吧,如有不理解的地方,欢迎在下方进行评论留言!!!