2018 蓝桥杯省赛 B 组模拟赛(一)

A. 结果填空:年龄 分值: 3
B. 结果填空:开关灯 分值: 7
C. 结果填空:U型数字 分值: 9
D. 代码填空:LIS 分值: 11
E. 代码填空:全排列 分值: 13
F. 结果填空:数独 分值: 16
G. 数列求值 分值: 15
H. 封印之门 分值: 20
I. 天上的星星 分值: 25
J. 青出于蓝胜于蓝 分值: 31

A. 结果填空:年龄 答案:1
今天蒜头君带着花椰妹和朋友们一起聚会,当朋友们问起年龄的时候,蒜头君打了一个哑谜(毕竟年龄是女孩子的隐私)说:“我的年龄是花椰妹年龄个位数和十位数之和的二倍”。

花椰妹看大家一脸懵逼,就知道大家也不知道蒜头君的年龄,便连忙补充道:“我的年龄是蒜头君个位数和十位数之和的三倍”。

请你计算:蒜头君和花椰妹年龄一共有多少种可能情况?

提醒:两位的年龄都是在 [10,100)[10,100) 这个区间内。

计算代码:

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;


int main(){
    int num=0;
    for(int i=10;i<100;i++){
        for(int j=10;j<100;j++){
            int a=i%10+i/10;
            int b=j%10+j/10;
            if((i==b*2)&&(j==a*3)){
                num++;
                //cout<<i<<endl<<j<<endl;
            }
        }
    }
    cout<<num<<endl;
    return 0;
}

原题填空代码:

#include <iostream>
using namespace std;
int main() {
    cout << "1" << endl;
    return 0;
}

B. 结果填空:开关灯 答案:571
蒜头君今天回到了老家的大宅院,老家的灯还是那中拉线的灯(拉一次为亮,再拉一次就灭),蒜头君觉得无聊。把 10001000 盏灯 33 的倍数拉了一次,55 的倍数拉了一次,7的倍数拉了一次(灯得的编号从 1-10001−1000,灯的初始状态都是亮的)。这个时候蒜头君在想还剩下几盏灯还在亮着?

提示:请不要输出多余的符号。

计算代码:

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;
bool a[1010];

int main(){
    int num=0;
    for(int i=1;i<=1000;i++)    a[i]=true;
    for(int i=1;i<=1000;i++){
        if(i%3==0)   a[i]=!a[i];
    }
    for(int i=1;i<=1000;i++){
        if(i%5==0)   a[i]=!a[i];
    }
    for(int i=1;i<=1000;i++){
        if(i%7==0)   a[i]=!a[i];
    }
    for(int i=1;i<=1000;i++){
        if(a[i]==true)   num++;
    }
    cout<<num<<endl;
    return 0;
}

原题代码:

#include <iostream>
using namespace std;
int main() {
    cout << "571" << endl;
    return 0;
}

C. 结果填空:U型数字 答案: 8193
最近蒜头君喜欢上了U型数字,所谓U型数字,就是这个数字的每一位先严格单调递减,后严格单调递增。比如 212212 就是一个U型数字,但是 333333, 9898, 567567, 3131331313,就是不是U型数字。

现在蒜头君问你,[1,100000][1,100000] 有多少U型数字?

提示:请不要输出多余的符号。
计算代码:

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;

int main(){
    int num=0;
    for(int i=100;i<=999;i++){
        int t=i;
        int a=t%10;
        t/=10;
        int b=t%10;
        t/=10;
        int c=t%10;
        if(c>b&&a>b)    num++;
    }
    for(int i=1000;i<=9999;i++){
        int t=i;
        int a=t%10;
        t/=10;
        int b=t%10;
        t/=10;
        int c=t%10;
        t/=10;
        int d=t%10;
        if(d>c&&b>c&&a>b)   num++;
        if(d>c&&c>b&&a>b)   num++;
    }
    for(int i=10000;i<=99999;i++){
        int t=i;
        int a=t%10;
        t/=10;
        int b=t%10;
        t/=10;
        int c=t%10;
        t/=10;
        int d=t%10;
        t/=10;
        int e=t%10;
        if(a>b&&b>c&&c<d&&d<e)  num++;
        if(e>d&&c>d&&b>c&&a>b)  num++;
        if(a>b&&c>b&&d>c&&e>d)  num++;
    }
    cout<<num<<endl;
    return 0;
}

原题代码:

#include <iostream>
using namespace std;
int main() {
    cout << "8193" << endl;
    return 0;
}

D. 代码填空:LIS 答案:f[i]=max(f[i],f[j]+1);
LIS是最长上升子序列。什么是最长上升子序列? 就是给你一个序列,请你在其中求出一段最长严格上升的部分,它不一定要连续。

就像这样:22, 33, 44, 77 和 22, 33, 44, 66 就是序列 22 55 33 44 11 77 66 的两个上升子序列,最长的长度是 44。
题目代码:

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

int f[10000], b[10000];
int lis(int n) {
    memset(f, 0, sizeof f);
    int res = 0;
    for (int i = 0; i < n; ++i) {
        for (int j = 0; j < i; ++j) {
            if (b[j] < b[i]) {
                f[i]=max(f[i],f[j]+1);
            }
        }
        res = max(res, f[i]);
    }
    return res+1;
}
int main() {
    int n;
    scanf("%d", &n);
    for (int i = 0; i < n; ++i) {
        scanf("%d", b + i);
    }
    printf("%d\n", lis(n));
    return 0;
}

E. 代码填空:全排列 答案:str[i] == str[j] && vis[j]
相信大家都知道什么是全排列,但是今天的全排列比你想象中的难一点。我们要找的是全排列中,排列结果互不相同的个数。比如:aab 的全排列就只有三种,那就是aab,baa,aba。

代码框中的代码是一种实现,请分析并填写缺失的代码。

题目代码:

#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
const int N=1e3;
char str[N], buf[N];//buffer
int vis[N], total, len;
void arrange(int num) {
    if (num == len){
        printf("%s\n", buf);
        total++;
        return;
    }
    for (int i = 0; i < len; ++i) {
        if (!vis[i]) {
            int j;
            for (j = i + 1; j < len; ++j) {
                if (str[i] == str[j] && vis[j]) {
                    break;
                }
            }
            if (j == len) {
                vis[i] = 1;
                buf[num] = str[i];
                arrange(num + 1);
                vis[i] = 0;
            }
        }
    }
}
int main() {
    while (~scanf("%s",str)) {
        len = strlen(str);
        sort(str, str + len);
        total = 0;
        buf[len] = '\0';
        arrange(0);
        printf("Total %d\n", total);
    }
    return 0;
}

F. 结果填空:数独
蒜头君今天突然开始还念童年了,想回忆回忆童年。他记得自己小时候,有一个很火的游戏叫做数独。便开始来了一局紧张而又刺激的高阶数独。蒜头君做完发现没有正解,不知道对不对? 不知道聪明的你能否给出一个标准答案?

标准数独是由一个给与了提示数字的 9 \times 99×9 网格组成,我们只需将其空格填上数字,使得每一行,每一列以及每一个 3 \times 33×3 宫都没有重复的数字出现。

《2018 蓝桥杯省赛 B 组模拟赛(一)》

输出这个数独得正解,输出格式如下:

//* 2 6 * * * * * *
//* * * 5 * 2 * * 4
//* * * 1 * * * * 7
//* 3 * * 2 * 1 8 *
//* * * 3 * 9 * * *
//* 5 4 * 1 * * 7 *
//5 * * * * 1 * * *
//6 * * 9 * 7 * * *
//* * * * * * 7 5 *
把上面的 * 替换成 1 – 91−9 就可以了

提醒:两个数字之间要有一个空格,其他地方不要输出多余的符号。

本题答案不唯一,符合要求的答案均正确

原题代码

#include <iostream>
using namespace std;
int main() {
    cout << "4 2 6 7 9 3 8 1 5" << endl;
    cout << "3 7 1 5 8 2 6 9 4" << endl;
    cout << "8 9 5 1 6 4 2 3 7" << endl;
    cout << "7 3 9 4 2 5 1 8 6" << endl;
    cout << "1 6 8 3 7 9 5 4 2" << endl;
    cout << "2 5 4 8 1 6 3 7 9" << endl;
    cout << "5 8 7 2 4 1 9 6 3" << endl;
    cout << "6 1 3 9 5 7 4 2 8" << endl;
    cout << "9 4 2 6 3 8 7 5 1" << endl;
    return 0;
}

G. 数列求值
《2018 蓝桥杯省赛 B 组模拟赛(一)》
样例输入1

1
50.50 25.50
10.15
样例输出1

27.85
样例输入2

2
-756.89 52.52
172.22 67.17
样例输出2

-761.49

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;

double a[1010];
int main(){
    int n;
    double y,temp;
    scanf("%d",&n);
    scanf("%lf%lf",&a[0],&y);
    a[1]=0;
    for(int i=2;i<=n+1;i++)  {
        scanf("%lf",&temp);
        a[i]=2*a[i-1]-a[i-2]+2*temp;
    }
    printf("%.2f\n",(y-a[n+1])/(n+1));
    return 0;
}

H. 封印之门
蒜头君被暗黑军团包围在一座岛上,所有通往近卫军团的路都有暗黑军团把手。幸运的是,小岛上有一扇上古之神打造的封印之门,可以通往近卫军团,传闻至今没有人能解除封印。

封印之门上有一串文字,只包含小写字母,有 kk 种操作规则,每个规则可以把一个字符变换成另外一个字符。经过任意多次操作以后,最后如果能把封印之门上的文字变换成解开封印之门的文字,封印之门将会开启。

蒜头君战斗力超强,但是不擅计算,请你帮忙蒜头君计算至少需要操作多少次才能解开封印之门。

输入格式

输入第一行一个字符串,长度不大于 10001000,只包含小写字母,表示封印之门上的文字。

输入第二行一个字符串,只包含小写字母,保证长度和第一个字符串相等,表示能解开封印之门的文字。

输入第三行一个整数 k(0 \le k \le 676)k(0≤k≤676)。

接下来 kk 行,每行输出两个空格隔开的字符 aa, bb,表示一次操作能把字符 aa 变换成字符 bb。

输出格式

如果蒜头君能开启封印之门,输出最少的操作次数。否则输出一行 -1−1。

样例输入

abcd
dddd
3
a b
b c
c d
样例输出

6

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;

int mapp[30][30];

string s1,s2;
int main(){
    cin>>s1;
    cin>>s2;
    for(int i=0;i<26;i++){
        for(int j=0;j<36;j++){
            if(i==j) mapp[i][j]=0;
            else mapp[i][j]=INF;
        }
    }
    int k;
    scanf("%d",&k);
    for(int i=0;i<k;i++){
        getchar();
        char a,b;
        scanf("%c %c",&a,&b);
        if(a!=b)    mapp[a-'a'][b-'a']=1;
    } 
    for(int t=0;t<26;t++){
        for(int i=0;i<26;i++){
            for(int j=0;j<26;j++){
                mapp[i][j]=min(mapp[i][j],mapp[i][t]+mapp[t][j]);
            }
        }
    }
    int ans=0;
    for(int i=0;i<s1.size();i++){
        if(mapp[s1[i]-'a'][s2[i]-'a']>=INF){
            printf("-1\n");
            return 0;
        }
        ans+=mapp[s1[i]-'a'][s2[i]-'a'];
    }
    printf("%d\n",ans);

    return 0;
}

I. 天上的星星
在一个星光摧残的夜晚,蒜头君一颗一颗的数这天上的星星。

蒜头君给在天上巧妙的画了一个直角坐标系,让所有的星星都分布在第一象。天上有 nn 颗星星,他能知道每一颗星星的坐标和亮度。

现在,蒜头君问自己 qq 次,每次他问自己每个矩形区域的星星的亮度和是多少(包含边界上的星星)。

《2018 蓝桥杯省赛 B 组模拟赛(一)》

输入格式

第一行输入一个整数 n(1 \le n \le 50000)n(1≤n≤50000) 表示星星的数量。

接下里 nn 行,每行输入三个整数x,y,w(0≤x,y,w≤2000),表示在坐标 (x,y)(x,y) 有一颗亮度为 ww 的星星。注意一个点可能有多个星星。

接下来一行输入一个整数q(1≤q≤50000),表示查询的次数。
接下来 qq 行,每行输入四个整数x1,y1,x2,y2,其中 (x 1,y1) 表示查询的矩形的左下角的坐标,(x_2, y_2)(x 2,y2) 表示查询的矩形的右上角的坐标,
20000≤x 1≤x 2 ≤2000,
20000≤y1≤y2≤2000。

输出格式

对于每一次查询,输出一行一个整数,表示查询的矩形区域内的星星的亮度总和。

样例输入

5
5 0 6
7 9 7
8 6 13
9 7 1
3 0 19
4
0 8 7 9
0 0 7 10
2 7 10 9
5 4 7 5
样例输出

7
32
8
0

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

const int MAX = 1e6+10;
const int INF = 0x3fffffff;
int mapp[2010][2010];
int dp[2010][2010];
int n;
int main(){
    cin>>n;
    int x,y,v;
    memset(dp,0,sizeof(dp));
    for(int i=0;i<n;i++){
        scanf("%d%d%d",&x,&y,&v);
        mapp[x+1][y+1]+=v;
    }
    for(int i=0;i<2010;i++){
        for(int j=0;j<2010;j++){
            dp[i][j]=dp[i-1][j]+dp[i][j-1]-dp[i-1][j-1]+mapp[i][j];
        }
    }
    int q;
    int x1,x2,y1,y2;
    scanf("%d",&q);
    while(q--){
        scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
        x1++, y1++, x2++, y2++;
        int ans = dp[x2][y2] - dp[x1-1][y2] - dp[x2][y1-1] + dp[x1-1][y1-1];
        printf("%d\n",ans);
    }
    return 0;
}
    原文作者:B树
    原文地址: https://blog.csdn.net/l18339702017/article/details/79445143
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞