• 博客园logo
  • 会员
  • 众包
  • 新闻
  • 博问
  • 闪存
  • 赞助商
  • HarmonyOS
  • Chat2DB
    • 搜索
      所有博客
    • 搜索
      当前博客
  • 写随笔 我的博客 短消息 简洁模式
    用户头像
    我的博客 我的园子 账号设置 会员中心 简洁模式 ... 退出登录
    注册 登录
百事可爱
一起努力鸭~~~
博客园    首页    新随笔    联系   管理    订阅  订阅
2015年蓝桥杯 Java 省赛试题及答案 C组

题目1.

Excel 表的格子很多,为了避免把某行的数据和相邻行混淆,可以采用隔行变色的样式。
小明设计的样式为:第1行蓝色,第2行白色,第3行蓝色,第4行白色,…
现在小明想知道,从第21行到第50行一共包含了多少个蓝色的行。
请你直接提交这个整数,千万不要填写任何多余的内容。

public static void main(String[] args) {
		int c=0;
		 for(int i=21;i<=50;i++) {
			 if(i%2!=0) c++;//奇数行进行jishu
		 }
		 System.out.println(c);
	}

题目2.

有些数字的立方的末尾正好是该数字本身。
比如:1,4,5,6,9,24,25,…
请你计算一下,在10000以内的数字中(指该数字,并非它立方后的数值),符合这个特征的正整数一共有多少个。
请提交该整数,不要填写任何多余的内容。
代码实现:

package 蓝桥2015;
 
//数字的立方的末尾正好是该数字本身。在10000以内的数字中,这个特征的正整数一共有多少个?
/*此数字若是1位数,那可以很快的到此数的三次方的最后一个数 String.charAt(s.length()-1)
 * 所以此题:
 * 1. 要知道此数字是几位数?
 * 2. 要从此数的三次方的最后截取几位数?截取后得到的数字看是否为此数字?*/
public class T2 {
	
	public static void main(String[] args) {
		    int c = 0;
		 for(long i=1;i<=10000;i++) {
			 long m3 = i*i*i;
			 String strNum = i+"";
			 String strM3 =  m3+"";
			 //String.substring(beginIndex),从起始下标beginIndex开始“从前往后”截取字符串
			 //beginIndex = strM3.length()-strNum.length();
			 String strLast = strM3.substring(strM3.length()-strNum.length());
			 if(strLast.equals(strNum)) {//String已经重写了equals方法,可以直接比较内容
				 c++;
			 }
		 }
		System.out.println(c);	  
		}
//36		 
}
//int型为有符号32位整数,占4个字节,取值范围在-2,147,483,648~2,147,483,647之间。
//Integer.parseInt(String s) 将String转为int
// String.valueOf 可以将许多类型转为 String

题目4

两个整数做除法,有时会产生循环小数,其循环部分称为:循环节。
比如,11/13=6=>0.846153846153… 其循环节为[846153] 共有6位。
下面的方法,可以求出循环节的长度。
请仔细阅读代码,并填写划线部分缺少的代码。

	public static int f(int n, int m)
	{
		n = n % m;
		Vector v = new Vector();

		for(;;)
		{
			v.add(n);
			n *= 10;
			n = n % m;
			if(n==0) return 0;
			if(v.indexOf(n)>=0)  _________________________________ ;  //填空
		}
	}

代码实现:

package 蓝桥2015;

import java.util.Vector;
//    11/13=6=>0.846153846153… 其循环节为[846153] 共有6位。

public class T5 {

	public static void main(String[] args) {
		System.out.println(f(11, 13));
		System.out.println(f(7, 18));		 
	}
//6 1
	// 下面的方法,可以求出循环节的长度。
	public static  int f(int n, int m)
	{
		n = n % m;
		Vector v = new Vector();

		for( ; ; )
		{
			v.add(n);
			n *= 10;
			n = n % m;
			if(n==0) return 0;
			if(v.indexOf(n)>=0)  return v.size() - v.indexOf(n);  //填空
		}
	}
} 
/*
 * 分析: 1. Vector v集合中存放了什么元素? 
 * f(11, 13); 
 *  public static void f(int n, int m)
	{
		n = n % m;
		Vector v = new Vector();

		for(int i=1;i<=15;i++)
		{
			v.add(n);
			n *= 10;
			n = n % m;
//			if(n==0) return 0;
//			if(v.indexOf(n)>=0)   ;  //填空
		}
		 System.out.println(v);
	}
}
运行结果:
[11, 6, 8, 2, 7, 5, 11, 6, 8, 2, 7, 5, 11, 6, 8]
 8,  4, 6, 1, 5, 3, 8,  4, 6, 1, 5, 3
 * 
 * 得出结论:
 * 集合元素循环节的长度 等于  小数循环节的长度
 * 2. 循环节不是都从小数点后第一位开始循环的!!
 * 比如:f(7, 18);
 * [7, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16]
 * 它的循环节就是一位,从小数点后第二位开始循环的!!
 * 3. if(n==0) return 0; 表明两个数相除,结果小数位是有限的
 * 4. if(v.indexOf(n)>=0) 判断n是否在集合中出现过,出现则返回首次出现的下标 
 */

题目5

stringInGrid方法会在一个指定大小的格子中打印指定的字符串。
要求字符串在水平、垂直两个方向上都居中。
如果字符串太长,就截断。
如果不能恰好居中,可以稍稍偏左或者偏上一点。
下面的程序实现这个逻辑,请填写划线部分缺少的代码。

	public static void stringInGrid(int width, int height, String s)
	{
		if(s.length()>width-2) s = s.substring(0,width-2);
		System.out.print("+");
		for(int i=0;i<width-2;i++) System.out.print("-");
		System.out.println("+");

		for(int k=1; k<(height-1)/2;k++){
			System.out.print("|");
			for(int i=0;i<width-2;i++) System.out.print(" ");
			System.out.println("|");
		}

		System.out.print("|");

		String ff = _______________________________________________________;  //填空
		System.out.print(String.format(ff,"",s,""));

		System.out.println("|");

		for(int k=(height-1)/2+1; k<height-1; k++){
			System.out.print("|");
			for(int i=0;i<width-2;i++) System.out.print(" ");
			System.out.println("|");
		}

		System.out.print("+");
		for(int i=0;i<width-2;i++) System.out.print("-");
		System.out.println("+");
	}

对应的输出结果应该是:

+------------------+
|                  |
|     abcd1234     |
|                  |
|                  |
+------------------+
分析:
字符串在水平上左右都空出5格,实现居中,在竖直上,上方是一行,而下方是两行,所以就偏上

代码实现:

package 蓝桥2015;

public class T5 {

	public static void main(String[] args) {
		 stringInGrid(20, 6, "abcd1234");
		 
	}	
	 
	public static void stringInGrid(int width, int height, String s)
	{
		//打印第一行
		if(s.length()>width-2) s = s.substring(0,width-2);
		System.out.print("+");
		for(int i=0;i<width-2;i++) System.out.print("-");
		System.out.println("+");
		//打印第二行
		for(int k=1; k<(height-1)/2;k++){
			System.out.print("|");
			for(int i=0;i<width-2;i++) System.out.print(" ");
			System.out.println("|");
		}
		
		//可以判断出,此处是打印包含了字符串的那一行
		System.out.print("|");
		  //此处打印  "空格 加 字符串 加 空格"
		 // “动态地”计算出字符串的左右应该控制多少空格 String ff="%n1s %s %n2s" n1和n2代表左右空格数
		//width减去边界2,再减去字符串的长度 除以2,若除尽,则n1=n2 若除不尽,偏左,就是按照结果赋给n1 剩余长度赋给n2
		int yu = width-2-s.length();
		String ff = "%" +(yu/2)+"s%s%"+(yu-(yu/2))+"s";  //填空
		System.out.print(String.format(ff,"",s,""));
		
//public static String format(String format, Object... args) 通过前面的像%d这样的实现对后面输出类型及长度的控制
//		%s 指定后面参数为字符串类型  %2s 若对空字符串,则就是空出两格 就是控制空格的数量
		
		System.out.println("|");
		
		for(int k=(height-1)/2+1; k<height-1; k++){
			System.out.print("|");
			for(int i=0;i<width-2;i++) System.out.print(" ");
			System.out.println("|");
		}
		System.out.print("+");
		for(int i=0;i<width-2;i++) System.out.print("-");
		System.out.println("+");
	}
}

题目6

小明发现了一个奇妙的数字。它的平方和立方正好把0~9的10个数字每个用且只用了一次。
你能猜出这个数字是多少吗?
请填写该数字,不要填写任何多余的内容。
代码实现:

package 蓝桥2015;

import java.util.HashSet;
import java.util.Set;

//它的平方和立方正好把0~9的10个数字每个用且只用了一次。

/*fenxi :
 * 1. 首先此数的范围不知???
 * 2. 保证平方和立方两个数 的总长度是10,每个用且只用了一次???
 解决:
 思路:在某个范围包含此数内循环,在循环中判断条件
 1. 先将循环范围定100,因为100的平方和立方两个数的总长度已经超过10
 2. 利用字符串的拼接,Set集合的不可重复*/
public class T6 {
//	static Set<Character> set = new HashSet<>();放在此处的结果是49
	public static void main(String[] args) {
		for (int i = 1; i <= 100; i++) {
			String m2 = i * i + "";
			String m3 = i * i * i + "";
			String m = m2 + m3;// 因为是数学运算,所以一定是只包括0~9的数字
			if (m.length() != 10) {
				continue;
			}
			if (check(m)) {
				System.out.println(i);
				break;
			}
		}
	}

	// 判断 是否0~9的10个数字只用了一次。
	public static boolean check(String string) {
		Set<Character> set = new HashSet<>();//放在此处运行结果才正确 69
		for (int i = 0; i < string.length(); i++) {
			set.add(string.charAt(i));
		}
		return set.size() == 10;
	}
}

题目7

我们都知道:1+2+3+ … + 49 = 1225
现在要求你把其中两个不相邻的加号变成乘号,使得结果为2015

比如:

1+2+3+…+10*11+12+…+27*28+29+…+49 = 2015就是符合要求的答案。

请你寻找另外一个可能的答案,并把位置靠前的那个乘号左边的数字提交(对于示例,就是提交10)。

注意:需要你提交的是一个整数,不要填写任何多余的内容。
代码实现:

package 蓝桥2015;

//1+2+3+ … + 49 = 1225,你把其中两个不相邻的加号变成乘号,使得结果为2015
//1+2+3+…+10*11+12+…+27*28+29+…+49 = 2015就是符合要求的答案。
//请你寻找另外一个可能的答案,并把位置靠前的那个乘号左边的数字提交(对于示例,就是提交10)。
/*silu:
 * 1.
 * 外循环是第一个乘号左边的数字x,那它右边的数字是x+1; x不可以取49,48,同时47也不行,因为要求是“两个不相邻”的加号变成乘号
 * 内循环是第二个乘号左边的数字y那它右边的数字是y+1;  若x取1,则y的最小值是3; y=x+2;
 * 2.
 * 1+2+3+…+10+11+12+…+27+28+29+…+49 = 1225
 * 1+2+3+…+10*11+12+…+27*28+29+…+49 = 2015 它没有加10+11和27+28 加了10*11和27*28
 * 所以可以用 2015-(10+11和27+28)+(10*11和27*28)=2015
 * 就对应了 x ,x+1,y,y+1
 * 
 **/
public class T7 {
	
	public static void main(String[] args) {
		for (int x = 1; x <= 46; x++) {
			for (int y = x + 2; y <= 48; y++) {
				// 确定了x,x+1,y,y+1 可以用
				int result = 1225 - x - (x + 1) - y - (y + 1) + x * (x + 1) + y * (y + 1);
				if (result == 2015) {
					System.out.println(x);
				}
			}
		}
	}
/*10
16
*/
}

题目8:(规律性强)

X星球居民小区的楼房全是一样的,并且按矩阵样式排列。其楼房的编号为1,2,3…
当排满一行时,从下一行相邻的楼往反方向排号。
比如:当小区排号宽度为6时,开始情形如下:

1 2 3 4 5 6
12 11 10 9 8 7
13 14 15 …

我们的问题是:已知了两个楼号m和n,需要求出它们之间的最短移动距离(不能斜线方向移动)

输入为3个整数w m n,空格分开,都在1到10000范围内

w是指小区排号的宽度

要求输出一个整数,表示m n 两楼间最短移动距离。

例如:
用户输入:
6 8 2
则,程序应该输出:
4

分析:其中一条路径:8先往上走一步,在往左走3步,加起来就是4步

8的行号是2,列号是5;

2的行号是1,列号是2;

(2-1)+(5-2)=4

结论:行号之差的绝对值 加上列号之差的绝对值 就是两楼间最短移动距离。

代码实现:

package 蓝桥2015;

import java.util.Scanner;

//输入为3个整数w m n,两个楼号m和n,w是指小区排号的宽度,一行有多少房子
//结论:——————————————————————————————————————————————————————————————————
//行号之差的绝对值 加上列号之差的绝对值  就是两楼间最短移动距离。
//所以需要计算:m行号,m列号,n行号,n列号
//行号:需要分情况讨论:房子的编号/宽度 是否可以除尽:(1)除不进:房子的编号/宽度+1 (2)可以除尽:房子的编号/宽度
//列号:需要分奇数和偶数行讨论:
//(1)奇数行:当前的编号-当前行中编号的最小值    当前行中编号的最小值就是:w*(行号-1)+1
//(2) 偶数行:当前行中编号的最大值-当前的编号   当前行中编号的最大值就是:w * 行号 

public class T8 {

	public static void main(String[] args) {
		 Scanner scanner = new Scanner(System.in);
		 int w = scanner.nextInt();
		 int m = scanner.nextInt();
		 int n = scanner.nextInt();
		 int mRow = m%w==0 ? m/w :m/w+1; //计算第一个房子的行号
		 int nRow = n%w==0 ? n/w :n/w+1; //计算第二个房子的行号
		 int mCol = 0;//计算第一个房子的列号
		 if(mRow%2==1) {//奇数行
			 mCol = m -(w*(mRow-1)+1);
		 }
		 else {
			 mCol = w*mRow-m;
		 }
		 
		 int nCol = 0;//计算第二个房子的列号
		 if(nRow%2==1) {//奇数行
			 nCol =  n -(w*(nRow-1)+1);
		 }
		 else {
			 nCol = w*nRow-n;
		 }
		 
		 int r = Math.abs((mRow-nRow))+Math.abs((mCol-nCol));
		 System.out.println(r);
	}
}

题目9:(规律性强)

小明希望用星号拼凑,打印出一个大X,他要求能够控制笔画的宽度和整个字的高度。
为了便于比对空格,所有的空白位置都以句点符来代替。

要求输入两个整数m n,表示笔的宽度,X的高度。用空格分开(0<m<n, 3<n<1000, 保证n是奇数)
要求输出一个大X

例如,用户输入:
3 9
程序应该输出:

***.....***
.***...***.
..***.***..
...*****...
....***....
...*****...
..***.***..
.***...***.
***.....***
jiexi :笔的宽度为3,就是每笔画占了3个星号

代码实现:

package 蓝桥2015;

import java.util.Scanner;

//要求输入两个整数m n,表示笔的宽度,X的高度。。用空格分开(0<m<n, 3<n<1000, 保证n是奇数)
//要求输出一个大X 
/*silu:
 * 将整个X看作是一个二维数组,先将数组中的每个元素都用.来初始化,然后去找*所在的位置,再进行替换:
 * 需要分:从左上到右下 和 右上到左下
 * 其中,从左上到右下:
 * 行号为0 :*号的第二维下标变化:0到2
 * 行号为1 :*号的第二维下标变化:1到3
 * 行号为2 :*号的第二维下标变化:2到4
 * *号的第二维下标:起始从行号开始 ,打印m个
 * 
 *  其中,从右上到左下:
 * 行号为0 :*号的第二维下标变化:8到10 10=11-0-1 11就是总列数 总列数-行号-1
 * 行号为1 :*号的第二维下标变化:7到9  9=11-1-1          总列数-行号-1  
 * 行号为2 :*号的第二维下标变化:6到8
 * *号的第二维下标:结束坐标从总列数-行号-1开始 ,倒着循环打印m个**/
public class T9 {

	public static void main(String[] args) {

		Scanner scanner = new Scanner(System.in);

		int m = scanner.nextInt();// 笔的宽度
		int n = scanner.nextInt();// X的高度
		// 定义为二维数组 第一维的长度就是行数,就是X的高度;二维就是每行有多少个元素 看样例中间行是4+3+4 3就是m 4可以用 高度n/2
		char[][] arr = new char[n][n / 2 * 2 + m];
		// 先将数组中的每个元素都用.来初始化
		for (int i = 0; i < arr.length; i++) {
			for (int j = 0; j < arr[i].length; j++) {
				arr[i][j] = '.';
			}
		}

		for (int i = 0; i < arr.length; i++) {
			// 从左上到右下,进行*的替换
			for (int j = i; j < i + m; j++) {
				arr[i][j] = '*';
			}
			// 从右上到左下,进行*的替换
			for (int j = n / 2 * 2 + m - i - 1; j > n / 2 * 2 + m - i - 1 - m; j--) {
				arr[i][j] = '*';
			}
		}
		
		//输出:
		for (int i = 0; i < arr.length; i++) {
			for (int j = 0; j < arr[i].length; j++) {
				System.out.print(arr[i][j]); 
			}
			System.out.println();//换行
		}
	}
}
posted on 2022-03-31 09:45  精致猪猪侠  阅读(165)  评论(0)    收藏  举报
刷新页面返回顶部
博客园  ©  2004-2025
浙公网安备 33010602011771号 浙ICP备2021040463号-3