相关题目:
2016年第七届蓝桥杯真题解析JavaB组
2016年第七届蓝桥杯真题解析JavaC组
2017年第八届蓝桥杯真题解析JavaB组
2017年第八届蓝桥杯真题解析JavaC组
2018年第九届蓝桥杯真题解析JavaB组
2018年第九届蓝桥杯真题解析JavaC组
2019年第十届蓝桥杯真题解析JavaB组
2019年第十届蓝桥杯真题解析JavaC组
2020年第十一届蓝桥杯JavaB组(七月场)真题解析
2020年第十一届蓝桥杯JavaC组(七月场)真题解析
2020年第十一届蓝桥杯JavaB组(十月场)真题解析
2020年第十一届蓝桥杯JavaC组(十月场)真题解析
A:第几天
2000年的1月1日,是那一年的第1天。
那么,2000年的5月4日,是那一年的第几天?
思路:
判断2000年是否为闰年:
普通闰年:公历年份是4的倍数的,且不是100的倍数,为普通闰年。
(如2004、2020年就是闰年);
世纪闰年:公历年份是整百数的,必须是400的倍数才是世纪闰年
(如1900年不是世纪闰年,2000年是世纪闰年);
闰年共有366天(1-12月分别为31天;
29天,31天,30天,31天,30天,31天,31天,30天,31天,30天,
31天);
2000年是闰年,因此答案125
答案:125
B:方格计数
如图p1.png所示,在二维平面上有无数个1x1的小方格。
我们以某个小方格的一个顶点为圆心画一个半径为1000的圆。
你能计算出这个圆里有多少个完整的小方格吗?
拿右上半边距离,要判断一个方格是否在圆内,就要看这个方格的
右顶点离圆心的距离是否大于R,即i*i+j*j<=R*R,算出左半边后乘4
就是最后答案;
代码:
package JB2018;
public class 方格计数B {
public static void main(String[] args) {
int ans=0;
for(int i=1;i<=1000;i++) {
for(int j=1;j<=1000;j++) {
if(i*i+j*j<=1000000) {
ans++;
}
}
}
System.out.println(ans*4);
}
}
答案:3137548
C:复数幂
设i为虚数单位。对于任意正整数n,(2+3i)^n 的实部和虚部都是整数。
求 (2+3i)^123456 等于多少? 即(2+3i)的123456次幂,这个数字很大,要求精确表示。
答案写成 “实部±虚部i” 的形式,实部和虚部都是整数(不能用科学计数法表示),中间任何地方都不加空格,实部为正时前面不加正号。(2+3i)^2 写成: -5+12i,
(2+3i)^5 的写成: 122-597i
注意:需要提交的是一个很庞大的复数,不要填写任何多余内容。
思路:
以前没用过BigInteger,丝毫不晓得怎么用,看了一篇大佬的题解,
觉得很好我就不在关公面前耍大刀了,链接放这了
第九届蓝桥杯省赛–复数幂
代码:
1 import java.math.BigInteger;
2
3 public class ComplexPower {
4
5 public static void main(String[] args) {
6 BigInteger bigA = new BigInteger("2");
7 BigInteger bigB = new BigInteger("3");
8 BigInteger bigC = new BigInteger("2");
9 BigInteger bigD = new BigInteger("3");
10 System.out.println(f(bigA,bigB,bigC,bigD));
11 }
12
13 public static String f(BigInteger bigA, BigInteger bigB, BigInteger bigC, BigInteger bigD) {
14 int count = 1;
15 BigInteger sb = new BigInteger("0");
16 BigInteger xb = new BigInteger("0");
17 while(count<123456) {
18 sb = (bigA.multiply(bigC).subtract(bigB.multiply(bigD))) ;
19 xb = (bigB.multiply(bigC).add(bigA.multiply(bigD)));
20 bigC = sb;
21 bigD = xb;
22 count++;
23 }
24 return sb +""+ xb +"i"; //不用加字符串“+”、"-",因为运算本身自带符号
25 }
26 }
D:测试次数
x星球的居民脾气不太好,但好在他们生气的时候唯一的异常举动是:摔手机。
各大厂商也就纷纷推出各种耐摔型手机。x星球的质监局规定了手机必须经过耐摔测试,并且评定出一个耐摔指数来,之后才允许上市流通。
x星球有很多高耸入云的高塔,刚好可以用来做耐摔测试。塔的每一层高度都是一样的,与地球上稍有不同的是,他们的第一层不是地面,而是相当于我们的2楼。
如果手机从第7层扔下去没摔坏,但第8层摔坏了,则手机耐摔指数=7。
特别地,如果手机从第1层扔下去就坏了,则耐摔指数=0。
如果到了塔的最高层第n层扔没摔坏,则耐摔指数=n
为了减少测试次数,从每个厂家抽样3部手机参加测试。
某次测试的塔高为1000层,如果我们总是采用最佳策略,在最坏的运气下最多需要测试多少次才能确定手机的耐摔指数呢?
请填写这个最多测试次数。
注意:需要填写的是一个整数,不要填写任何多余内容。
说实话我实在没想到填空题这么难,这可能就是太菜了吧,
这里有一题有视频讲解y总的,这题大佬写的答案和y总的
视频教程链接放下面了:
鸡蛋的硬度——yxc
测试次数
E:快速排序
以下代码可以从数组a[]中找出第k小的元素。
它使用了类似快速排序中的分治算法,期望时间复杂度是O(N)的。
请仔细阅读分析源码,填写划线部分缺失的内容。
import java.util.Random;
public class Main{
public static int quickSelect(int a[], int l, int r, int k) {
Random rand = new Random();
int p = rand.nextInt(r - l + 1) + l;
int x = a[p];
int tmp = a[p]; a[p] = a[r]; a[r] = tmp;
int i = l, j = r;
while(i < j) {
while(i < j && a[i] < x) i++;
if(i < j) {
a[j] = a[i];
j--;
}
while(i < j && a[j] > x) j--;
if(i < j) {
a[i] = a[j];
i++;
}
}
a[i] = x;
p = i;
if(i - l + 1 == k) return a[i];
if(i - l + 1 < k) return quickSelect( _________________________________ ); //填空
else return quickSelect(a, l, i - 1, k);
}
public static void main(String args[]) {
int [] a = {1, 4, 2, 8, 5, 7};
System.out.println(quickSelect(a, 0, 5, 4));
}
}
注意:只提交划线部分缺少的代码,不要抄写任何已经存在的代码或符号。
思路:
Math.random()来随机选择[0,1)内的任意数,如果需要挑出[5,99]
闭区间的任意整数,则可以这样设置
int num = 5 + rand.nextInt(99 + 1 - 5);
然后看一下别人的把,我太菜了,没想出来
(第九届)第五题-快速排序
答案:a, i+1, r, r-(i-l+1)
F:递增三元组
给定三个整数数组
A = [A1, A2, … AN],
B = [B1, B2, … BN],
C = [C1, C2, … CN],
请你统计有多少个三元组(i, j, k) 满足:
【输入格式】
第一行包含一个整数N。
第二行包含N个整数A1, A2, … AN。
第三行包含N个整数B1, B2, … BN。
第四行包含N个整数C1, C2, … CN。
对于30%的数据,1 <= N <= 100
对于60%的数据,1 <= N <= 1000
对于100%的数据,1 <= N <= 100000 0 <= Ai, Bi, Ci <= 100000
【输出格式】
一个整数表示答案
【输入样例】
3
1 1 1
2 2 2
3 3 3
【输出样例】
27
思路:
1.这题暴力可以得30%的分数,要优化,这里用的是二分法,先全部排序
然后我们以B数组为基准,用二分在A数组中找第一个大于灯B[i]的数字下
标m,同理在C数组找第一个小于等于B[i]的数字下标n,然后
(m-1)*(B.length-n)就是B[i]这个点的所有满足的条件的三元组个数;
2.在用分的时候,下标的左右边界分别要是(0,n+1)因为有可能存在找不
到的情况,举个例子:A[]={3,3,3},B[1]=2,用二分的时候找不到,此时
left应该是等于零的,如果用边界是(1,n)就会有歧义
代码:
import java.util.Arrays;
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner input=new Scanner(System.in);
int n=input.nextInt();
int N=100010;
int a[]=new int[N];
int b[]=new int[N];
int c[]=new int[N];
for(int i=1;i<=n;i++){
a[i]=input.nextInt();
}
for(int i=1;i<=n;i++){
b[i]=input.nextInt();
}
for(int i=1;i<=n;i++){
c[i]=input.nextInt();
}
Arrays.sort(a,1,n+1);
Arrays.sort(b,1,n+1);
Arrays.sort(c,1,n+1);
long res=0;
for(int i=1;i<=n;i++){
//这样它之前的所有数都比b[i]小,用二分法
int left=0;
int right=n+1;
int mid=0;
while(left<right){
mid=(left+right)/2;
if(a[mid]>=b[i]){
right=mid;
}
else
{
left=mid+1;
}
}
//在c找最小的比b[i]大的值的下标
int left2=0;
int right2=n+1;
while(left2<right2){
mid=(left2+right2+1)/2;
if(c[mid]<=b[i]){
left2=mid;
}
else{
right2=mid-1;
}
}
if(left==0||left2==n+1)
continue;
else{
res+=((long)(left-1)*(n-left2));
}
}
System.out.println(res);
}
}
G:螺旋折线
如图p1.pgn所示的螺旋折线经过平面上所有整点恰好一次。
对于整点(X, Y),我们定义它到原点的距离dis(X, Y)是从原点到(X, Y)的螺旋折线段的长度。
例如dis(0, 1)=3, dis(-2, -1)=9
【输入格式】
X和Y
对于40%的数据,-1000 <= X, Y <= 1000
对于70%的数据,-100000 <= X, Y <= 100000
对于100%的数据, -1000000000 <= X, Y <= 1000000000
【输出格式】
输出dis(X, Y)
【输入样例】
0 1
【输出样例】
3
1.把图转换一下,就可以看出来里面的正方形的周长是公差为8的
等差数列,我们先把要求点的里面的所有正方形周长之和,再求
该点与这个点所在的正方形的左下角的距离,两者相加就是答案;
2.为什么是左下角,因为旋转之后原来的那个点变成左下角那个点,
算目标点与左下角那个点的距离,不能直接算要判断情况,因为为
变换之前图形是顺时针圈扩展的,我们算的时候也要按逆时针
“顺时针”算;
3.顺时针算到其所在正方形的左下角有两种情况,x<=y,和x>y两种,
第一种的情况是直接减去(-N,-N)这个坐标就行了,这个距离最短,
第二种是距离比较长的,正方形周长减去该点用第一种方法算的距离;
package JB2018;
import java.util.Scanner;
public class 螺旋折线 {
public static void main(String[] args) {
Scanner input=new Scanner(System.in);
int x=input.nextInt();
int y=input.nextInt();
int N=Math.max(Math.abs(x),Math.abs(y));//这个点所在第几个正方形
//前n-1个正方形的周长,根据等差数列前n项和变形得
int sum=4*N*(N-1);
//算该点与所在正方形左下角的距离
//左小角的坐标(-N,-N)
if(x<=y){//根据折叠规律,可得出当x<=y的时候直接减就好了
sum+=(x-(-N))+y-(-N);
}
else //拿周长减去 直接减所得的距离就是 最终的距离
{
sum+=(8*N-((x-(-N))+y-(-N)));
}
System.out.println(sum);
}
}
思路来源:zzzmj_
H:日志统计
小明维护着一个程序员论坛。现在他收集了一份"点赞"日志,日志共有N行。其中每一行的格式是:
ts id
表示在ts时刻编号id的帖子收到一个"赞"。
现在小明想统计有哪些帖子曾经是"热帖"。如果一个帖子曾在任意一个长度为D的时间段内收到不少于K个赞,小明就认为这个帖子曾是"热帖"。
具体来说,如果存在某个时刻T满足该帖在[T, T+D)这段时间内(注意是左闭右开区间)收到不少于K个赞,该帖就曾是"热帖"。
给定日志,请你帮助小明统计出所有曾是"热帖"的帖子编号。
【输入格式】
第一行包含三个整数N、D和K。
以下N行每行一条日志,包含两个整数ts和id。
对于50%的数据,1 <= K <= N <= 1000
对于100%的数据,1 <= K <= N <= 100000 0 <= ts <= 100000 0 <= id <= 100000
【输出格式】
按从小到大的顺序输出热帖id。每个id一行。
【输入样例】
7 10 2
0 1
0 10
10 10
10 1
9 1
100 3
100 3
【输出样例】
1
3
思路:
1.我们要判断一个帖子是不是热帖,就要知道它在某个
区间内是否点赞数大于等于K,而且这个区间还要有序才
能保证答答案的正确性,这就要把时间与对应的id,一
起排序,需要定义一个类,然后用ArrayList.sort去
排序;
class Ps implements Comparable<Ps>{
public int t;
public int id;
public Ps(int t,int id){
this.t=t;
this.id=id;
}
public int compareTo(Ps o){
return Integer.compare(t,o.t);
}
}
2.排好序后我们就在双指针加滑动窗口在规定的区间
里找,不能两重循环暴力找会超时,只能过百分之五
十的数据;
3.用j,i分别表示窗口的左右边界,每次遍历的时候
hot[ps[i].id]++;
当ps[i].t-ps[j].t>=D的时候窗口就要缩小,还要
把左边界所指的那个时间的对应的店铺热度减掉,即
hot[ps[j].id]--;
4.经过上述操作后如果当前时间点对应的店铺的热度
大于等于K,则表示这个店铺是热帖;
代码
import java.util.Arrays;
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner input=new Scanner(System.in);
int N=input.nextInt();
int D=input.nextInt();
int K=input.nextInt();
Ps[] logs = new Ps[N+1];
int ans[]=new int[1000000];
int hot[]=new int[1000000];
for(int i=0;i<N;i++){
int t=input.nextInt();
int id=input.nextInt();
logs[i] = new Ps(t,id);
}
Arrays.sort(logs,0,N);
for(int i=0,j=0;i<N;i++){
hot[logs[i].id]++;
while(logs[i].t-logs[j].t>=D){
hot[logs[j].id]--;
j++;
}
if(hot[logs[i].id]>=K){
ans[logs[i].id]=1;
}
}
for(int i=0;i<1000000;i++){
if(ans[i]==1)
System.out.println(i);
}
}
}
class Ps implements Comparable<Ps>{
public int t;
public int id;
public Ps(int t,int id){
this.t=t;
this.id=id;
}
public int compareTo(Ps o){
return Integer.compare(t,o.t);
}
}
I:全球变暖
你有一张某海域NxN像素的照片,".“表示海洋、”#"表示陆地,如下所示:
…
.##…
.##…
…##.
…####.
…###.
…
其中"上下左右"四个方向上连在一起的一片陆地组成一座岛屿。例如上图就有2座岛屿。
由于全球变暖导致了海面上升,科学家预测未来几十年,岛屿边缘一个像素的范围会被海水淹没。具体来说如果一块陆地像素与海洋相邻(上下左右四个相邻像素中有海洋),它就会被淹没。
例如上图中的海域未来会变成如下样子:
.......
.......
.......
.......
....#..
.......
.......
请你计算:依照科学家的预测,照片中有多少岛屿会被完全淹没。
【输入格式】
第一行包含一个整数N。 (1 <= N <= 1000)
以下N行N列代表一张海域照片。
照片保证第1行、第1列、第N行、第N列的像素都是海洋。
【输出格式】
一个整数表示答案。
【输入样例】
7
.......
.##....
.##....
....##.
..####.
...###.
.......
【输出样例】
1
1.用BFS找到所有大岛屿的下标并标记下边,记录所有大岛屿的个数用
countsum记录下来;
2.在块大岛屿中找是否存在一个小岛屿四面不环海,如果有用count记
录下来;
3.countsum-count就是最后答案;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Scanner;
public class Main {
public static int xx[]={0,-1,1,0,0};
public static int yy[]={0,0,0,-1,1};
static int count=0;
public static void main(String[] args) {
Scanner input=new Scanner(System.in);
int N=input.nextInt();
String []arr=new String[N];
char [][]map=new char[N][N];
for(int i=0;i<N;i++){
arr[i]=input.next();
map[i]=arr[i].toCharArray();
}
int [][]visited=new int[N][N];
int countsum=0;
for(int i=0;i<N;i++){
for(int j=0;j<N;j++){
if(visited[i][j]==0&&map[i][j]=='#') {
BFS(map, visited, i, j, N);
countsum++;
}
}
}
System.out.println(countsum-count);
}
public static void BFS(char [][]map,int [][]visited,int X,int Y,int N){
Queue<Integer> heng=new LinkedList<Integer>();
Queue<Integer> zong=new LinkedList<Integer>();
int startx=X;
int starty=Y;
visited[startx][starty]=1;
heng.offer(startx);
zong.offer(starty);
int isexist=0;//判断同一块岛屿中是否已经存在一个小岛屿四面不环海
while (!heng.isEmpty()){
int nowx=heng.poll();
int nowy=zong.poll();
//四个方向
for(int i=1;i<=4;i++){
int fowardx=nowx+xx[i];
int fowardy=nowy+yy[i];
if(fowardx<0||fowardx>=N)
continue;
else if(fowardy<0||fowardy>=N)
continue;
else if(visited[fowardx][fowardy]!=0)
continue;
else if(map[fowardx][fowardy]!='#')
continue;
heng.offer(fowardx);
zong.offer(fowardy);
visited[fowardx][fowardy] = 1;
//之前是否已经有过包围的点,若没有看看这个点是否被海水包围
if (isexist == 0) {
int flag = 0;
for (int k = 1; k <= 4; k++) {
if (map[fowardx + xx[k]][fowardy + yy[k]] == '.') {
flag = 1;
break;
}
}
//说明没有被海水包围
if (flag == 0) {
count++;
isexist++;
}
}
}
}
}
}
标题:堆的计数
我们知道包含N个元素的堆可以看成是一棵包含N个节点的完全二叉树。
每个节点有一个权值。对于小根堆来说,父节点的权值一定小于其子节点的权值。
假设N个节点的权值分别是1~N,你能求出一共有多少种不同的小根堆吗?
例如对于N=4有如下3种:
由于数量可能超过整型范围,你只需要输出结果除以1000000009的余数。
【输入格式】
一个整数N。
对于40%的数据,1 <= N <= 1000
对于70%的数据,1 <= N <= 10000
对于100%的数据,1 <= N <= 100000
【输出格式】
一个整数表示答案。
【输入样例】
4
【输出样例】
3
这题不适合我这个菜鸡,写不来看不懂