蓝桥杯练习2

  1. 问题 1095: The 3n + 1 problem
    考虑下面的算法生成一个数字序列。先从一个整数n。如果n是偶数,除以2,如果n是奇数,乘以3,并添加1。重复此过程,直到n = 1。例如,将对于n生成数的下列序列
    n= 22:22 11 34 17 52 26 13 40 20 10 5 16 8 4 2 1据推测(但尚未证实),该算法将对于每个整数n在n = 1终止。另外,在上述的例子中,22中的周期长度是16.给出任意两个数字i和j,确定i和j之间在所有数字的最大周期长度(包括两个端点)。
import java.util.Scanner;
//输入未说明大小顺序,因此需要先排序,否则错误33
public class Main {
	public static void main(String[] args) {
		Scanner sc = new Scanner(System.in);
		while (sc.hasNext()) {
			int start,end;
			int maxcount = 0;
			int a = sc.nextInt();
			int b= sc.nextInt();
			if(a>b) {
				end=a;
				start=b;
			}else {
				start=a;
				end=b;
			}
				
			for (int i = start; i <= end; i++) {
				int count = 1;
				int j = i;
				while (j != 1) {
					if (j % 2 == 0) {
						j /= 2;
						count++;
					} else {
						j = j * 3 + 1;
						count++;
					}
				}
				if (count > maxcount)
					maxcount = count;

			}
			System.out.println(a + " " + b + " " + maxcount);
		}
		sc.close();

	}
}
  1. 问题 1097: 蛇行矩阵
    易得出,最大数为1~n求和,从右上角依次向左下角递减,构造一个数组存放,注意输出格式
import java.util.Scanner;

public class Main {
	public static void main(String[] args) {
		int[][] num;
		Scanner sc = new Scanner(System.in);
		while (sc.hasNext()) {
			int n = sc.nextInt();
			int N = (n * n + n) / 2;
			num = new int[n][n];
			while (N > 0) {
				for (int i = n - 1; i >= 0; i--) {
					int x = 0;
					for (int y = i; y >= 0; y--, x++) {
						num[x][y] = N--;
					}
				}
			}
			for (int i = 0; i < n; i++) {
				int m=n-i;
				for (int j = 0; j < m; j++) {
					if(j==m-1)
						System.out.print(num[i][j]);
					else
						System.out.print(num[i][j]+" ");
				}
				System.out.println();
			}

		}
		sc.close();
	}
}

不使用数组的思路,行从0开始,列从1开始,则可推出
每行首位置数值=上一行首位置数值+本行行数(首行首位初始化为1)
每行非首位置数值=前一列数值+本行行数+本列列数

import java.util.Scanner;

public class Main {
	public static void main(String[] args) {
		Scanner sc = new Scanner(System.in);
		while (sc.hasNext()) {
			int daty = 1, datx = 1;
			int n = sc.nextInt();
			int m = n;
			for (int x = 0; x < n; x++) {

				for (int y = 1; y <= m; y++) {
					if (y == 1) {
						if (x != 0)
							daty += x;
						System.out.print(daty + " ");
						datx = daty;
					}

					else {
						datx += x + y;
						if (y == m)
							System.out.print(datx);
						else
							System.out.print(datx + " ");
					}
				}
				System.out.println();
				m--;
			}
		}
		sc.close();
	}
}
  1. 问题 1110: 2^k进制数

这个题困扰了我一天,查到的答案都很简略,果然是我太菜了==
题干说的很复杂,根据例子自己写一写应该可以理解,直接说做法
w/k即为完整的段数,若正好可以完整分段,则相当于从可表达的7个状态(1——2^k-1,因为必须从左向右递增,且最少两段,所以不取0)中选出i【2<=i<=w/k】个状态放置,即求组合数(取出不放回,不求顺序)C(7,i)【2<=i<=w/k】。
若w/k有余数,则最高位可表达的就是1——2^(w%k)个状态,若直接求最高位有值的可取数,以w=3,k=8而言,相当于最高位从1——3中取1,其余两位从2——7 6个状态中取两个+最高位取2,其余从3——7 5个状态取两个+……,计算相对复杂。所以采用减法思维,用最高位从1——7任选(这种情况就是C(7,3))减去最高位从不能用的状态4——7中任选(这种情况就是C(4,3))。
这里给出组合数的计算公式,代码中使用时将n!与(n-m)!约了一下
在这里插入图片描述

import java.util.Scanner;

public class Main {
	public static void main(String[] args) {
		Scanner scanner = new Scanner(System.in);
		while (scanner.hasNext()) {
			int k = scanner.nextInt();
			int w = scanner.nextInt();
			int h = w % k;// 多余的位数作为最高位
			int n = w / k + 1;// 此数值有多少位
			int max = (int) Math.pow(2, k) ;
			int high = (int) (Math.pow(2, h) - 1);
			long count = 0;
			if (k > 9 || k < 0)
				break;
			else {
				for (int i = 2; i < n; i++)
					count += c(max, i);
				if (high != 0) {
					count += (c(max, n) - c(max - high, n));
				}
				System.out.println(count);
			}
		}
	}

	public static long c(int max, int pos) {
		int count=1;
		for(int i=1;i<=pos;i++) {
			count*=(max-i);
		}
		for(int i=2;i<=pos;i++) {
			count/=i;
		}
		return count;
	}
}
发布了41 篇原创文章 · 获赞 1 · 访问量 1479

猜你喜欢

转载自blog.csdn.net/qq_44467578/article/details/103975727