java第七次作业





1.格雷码(Gray Code)序列

两个bit的格雷码通过一个bit的格雷码序列产生:原始序列前面加上"0",然后把原始序列反序,前面加上"1",最后放在一起形成两个bit的格雷码;

三个bit的格雷码用类似的方法从两个bit的格雷码产生。

本题要求生成指定bit的格雷码序列。

输入:

格雷码的位数n

输出:

对应的反射式格雷码(请按照题目中给出的方法生成),两种方法,供大家参考

(方法1:)

public class Main {
	public static void main(String[] args) {
		//位数
		int n = StdIn.readInt();
		//序列个数
		int m = (int) Math.pow(2,n);
		int[][] code = new int[m][n];
		gray(code, n, m);
		for (int i = 0; i < m; i++) {
			for (int j = 0; j < n; j++) {
				System.out.print(code[i][j]);
			}
			System.out.println();
		}
	}
	public static void gray(int[][] code, int n, int m) {
		if (n == 1) {
			code[0][0] = 0;
			code[1][0] = 1;
		}else{
			gray(code,n-1,m/2);
			for (int i = 0; i <m / 2; i++) {
				//数组移动
				for (int j = n-2; j >=0; j--) {
					code[i][j + 1] = code[i][j] ;
				}
				//最前位置加0
				code[i][0] = 0;
				//逆序
				for (int j = 0; j < n; j++) {
					code[m-i-1][j] = code[i][j] ;
				}
				//最前位置变1
				code[m-i-1][0] = 1;
			}
		}
	}
}
(方法2:)
public class Main {
	public static void graycode(int a, int b, int arr[][]) {// a=2 b=1 
		if (a == 1)
			return;
		for (int i = 0; i < a / 2; i++)
			for (int j = 0; j < 2; j++) {
				arr[i][b - 1] = 0;
				arr[a - i - 1][b - 1] = 1;
			}
		graycode(a / 2, b - 1, arr);

		for (int k = a / 2; k < a; k++)
			for (int j = 0; j < b - 1; j++)
				arr[k][j] = arr[a - k - 1][j];
	}
	public static void main(String[] args) {// N=3 M=8 
		int N = StdIn.readInt();
		int M = (int) Math.pow(2, N);
		int arry[][] = new int[M][N];
		Main.graycode(M, N, arry);
		for (int i = 0; i < M; i++) {
			for (int j = N - 1; j >= 0; j--)
				System.out.print(arry[i][j]);
			System.out.println();
		}
	}
}

2.第二类斯特林 (Stirling) 数

组合数学中一个典型的问题是:把从1到n标号的n个球放到k个无区别的盒子里,要求每个盒子里至少有一个小球,问不同的放法数量。例如,如果用A、B、C、D分别表示4个球,要分成两组(即放入无区别的盒子里),其方法有7种。

  1. {A,B},{C,D}
  2. {A,C},{B,D}
  3. {A,D},{B,C}
  4. {A},{B,C,D}
  5. {B},{A,C,D}
  6. {C},{A,B,D}
  7. {D},{A,B,C}

这个数量可以用第二类斯特林 (Stirling) 数来计算,表示为S(n,k),S(4,2)=7。

输入:

参数n,k(n≥k≥0)

输出:

对应的第二类斯特林数值

public class Main {
	public static void main(String[] args) {
		int n = StdIn.readInt();
		int k = StdIn.readInt();
		System.out.println(stirling(n,k));
	}
	public static int stirling(int n, int k) {
		if (n == 0 && k == 0) {
			return 1;
		} else if (n == 0 && k >= 1) {
			return 0;
		} else if (k == 0 && n >= 1) {
			return 0;
		} else {
			return k * stirling(n - 1, k) + stirling(n - 1, k - 1);
		}
	}
}


3. 整数分划

正整数n的一个分划是指把n表示成若干个正整数的和。这里的分划与顺序无关,例如6=5+1 和 6=1+5即被认为是同一种分划。另外,这个整数本身也算一种分划。

例如,正整数n=6,可以分划为

6
5+1
4+2, 4+1+1
3+3, 3+2+1, 3+1+1+1
2+2+2, 2+2+1+1, 2+1+1+1+1
1+1+1+1+1+1

输入:

待分解的正整数n

输出:

对应的排好序的分解,每行一个,中间用空格分开 (完全参考老师提供的答案)

public class Main {
	public static void main(String[] paramArrayOfString) {
		int i = StdIn.readInt();
		fun(i);
	}
	public static void fun(int num) {
		fun(num, num, "");
	}
	public static void fun(int num1, int num2, String str) {
		if (num1 == 0) {
			StdOut.println(str.substring(1));
			return;
		}
		for (int i = Math.min(num2, num1); i >= 1; --i) {
			fun(num1 - i, i, str + " " + i);
		}
	}
}



评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值