2021蓝桥杯B组部分题题解(比赛没参加, 小白一个,随便写写)


 

A题:空间

根据:

  1MB = 1024KB

  1KB = 1024B

  1B = 8bit

由题可知

  32bit = 4B

直接模拟即可

#include <iostream>
using namespace std;

int main ()
{
  cout << 256 * 1024 * 1024 / 4 <<endl;
  return 0;
}

 

答案:67108864

B题:卡片

定义十个下标0-9的数组,每个数组包含数字2021,可表示为每个0-9的数字有2021个。

定义i=1表示为从1开始排数,取 i mod 10 的余数,对于每个余数a[i % 10] -- 即可,直到把某个数字减完。

 1 #include <iostream>
 2 using namespace std;
 3 
 4 int main ()
 5 {
 6     int a[10] = {2021,2021,2021,2021,2021,2021,2021,2021,2021,2021};
 7     
 8     int res = 0;
 9     int i = 1;
10     while (i)
11     {
12         int k = i;
13         while (k)
14         {
15             if (a[k%10] == 0)
16             {
17                 cout << res <<endl;
18                 return 0;
19             }
20             a[k % 10] -- ;
21             k /= 10;
22 
23         }
24             res++;
25             i ++;
26     }
27     
28     return 0;
29 }

 

答案:3181

C题:直线

设直线方程y = kx + m;

根据直线性质:

斜率k = (y1 - y2) / (x1 - x2)

截距b = m

枚举每个点,这里需要注意的是,由于垂直线不存在斜率,所以当x1 = x2的时候不枚举。

定义Line结构体储存k,b。

在误差1e-8之内可算作同一条直线。

 1 #include <iostream>
 2 #include <cstring>
 3 #include <algorithm>
 4 #include <cmath>
 5 
 6 using namespace std;
 7 
 8 const int N = 200000;
 9 
10 int n;
11 struct Line
12 {
13     double k, b;
14     bool operator< (const Line& t) const
15     {
16         if (k != t.k) return k < t.k;
17         return b < t.b;
18     }
19 }l[N];
20 
21 int main()
22 {
23     for (int x1 = 0; x1 < 20; x1 ++ )
24         for (int y1 = 0; y1 < 21; y1 ++ )
25             for (int x2 = 0; x2 < 20; x2 ++ )
26                 for (int y2 = 0; y2 < 21; y2 ++ )
27                     if (x1 != x2)
28                     {
29                         double k = (double)(y2 - y1) / (x2 - x1);
30                         double b = y1 - k * x1;
31                         l[n ++ ] = {k, b};
32                     }
33 
34     sort(l, l + n);
35     int res = 1;
36     for (int i = 1; i < n; i ++ )
37         if (fabs(l[i].k - l[i - 1].k) > 1e-8 || fabs(l[i].b - l[i - 1].b) > 1e-8)
38             res ++ ;
39     cout << res + 20 << endl;
40 
41     return 0;
42 }

 

答案:40257

D题:货物摆放

用试除法枚举2021041820210418的每一个约数

直接遍历即可。

 1 #include <iostream>
 2 #include <vector>
 3 using namespace std;
 4 const int N = 1000010;
 5 vector<long long> q;
 6 
 7 int main ()
 8 {
 9     int res = 0;
10     long long n = 2021041820210418;
11     
12     for (long long i = 1 ; i * i <= n ; i ++ )
13     {
14         if (n % i == 0)
15         {
16             q.push_back(i);
17             if (n / i != i ) q.push_back(n / i);
18         }
19     }
20     
21     for (int a = 0 ; a < q.size() ; a++ )
22         for (int b = 0 ; b < q.size() ; b ++ )
23             for (int c = 0 ; c < q.size() ; c ++)
24                 {
25                     if (q[a] * q[b] * q[c] == n)
26                     res++;
27                 }
28                 
29                 cout << res <<endl;
30                 return 0;
31 }

 

答案:2430

F题:时间显示

题目只要求输出时分秒,所以可以先把N =/ 1000。

然后用N对一天之内的秒数取模,即 N %= 86400。

直接模拟即可。

#include <iostream>

using namespace std;

typedef long long LL;

int main()
{
    LL n;
    cin >> n;
    n /= 1000;
    n %= 86400;
    int h = n / 3600;
    n %= 3600;
    int m = n / 60;
    int s = n % 60;
    printf("%02d:%02d:%02d\n", h, m, s);
    return 0;
}

 H题:杨辉三角形

由于求的是数字第一次出现的位置,所以可以对杨辉三角轴对称切半,观察斜行。

不难发现除了第一斜行,每一斜行都是递增,因为C(n,m)n越大值越大,同理每一行也是递增。

 

 

 

 

根据杨辉三角性质可知:

1.每个数都会在杨辉三角的左半边出现

2.对于第n行第m个数字,其值为C(n-1,m-1)

3.在第35行18个时,C(34,17)> 109

上述可知,用二分可快速求出当前数第一次出现的次数。

 1 #include <iostream>
 2 using namespace std;
 3 typedef long long ll;
 4 
 5 int n;
 6 
 7 ll bsearch(int a, int b)
 8 {
 9     ll res = 1;
10     for(int i = a, j = 1; j <= b; i--, j++)
11     {
12         res = res * i / j;
13         if(res > n) return res;
14     }
15     return res;
16 }
17 
18 int check(int k)
19 {
20     ll l = 2 * k, r = n;
21     while(l < r) // 二分查找
22     {
23         int mid = l + r >> 1;
24         if(bsearch(mid, k) >= n)  r = mid;
25         else    l = mid + 1;
26     }
27     if(bsearch(r, k) != n)    return 0;
28     cout << r * (r + 1) / 2 + k + 1 << endl;
29     return 1;
30 }
31 
32 int main()
33 {
34     cin >> n;
35 
36     for(int k = 16; ; k--)
37     if(check(k))    break;
38     return 0;
39 }

 


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM