题目: 编写程序为火柴棍摆成的任意自然数生成一个最大数和最小数
原题:用火柴棍摆成自然数"1995",移动任意一根火柴得到最大数和最小数分别是多少。
程序结果:
火柴数字参考图:
题目分析:
最大数:
思路分析:
-
只能移动一根火柴,则最多只能改变两个数,最好的情况是直接将千位的数字变大,这样就生成的数便是最大的。
-
增大优先级:千位 > 百位 > 十位 > 个位
-
减小优先级:个位 > 十位 > 百位 > 千位
-
按增大优先级进行移动火柴,需要增加火柴则按减小优先级进行火柴的移动;需要减少火柴则按增大优先级进行移动火柴。
-
1
增加一横 变为7
-
2
移动自身 变为3
-
3
增加一竖 变为9
-
4
不可增大 -
5
增加一竖 变为9
-
6
移动自身 变为9
-
7
不可增大 -
8
减去一竖 变为9
-
9
为最大 无需改变 -
0
移动自身 变为9
代码实现:
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.print("请输入一个四位整数:");
int input = sc.nextInt();
int qian = input / 1000;
int bai = input / 100 % 10 ;
int shi = input / 10 % 10;
int ge = input % 10;
System.out.println("原数为: "+qian+" "+bai+" "+shi+" "+ge);
String max = max(qian, bai, shi, ge);
String min = min(qian, bai, shi, ge);
System.out.println("最大数: " + max);
System.out.println("最小数: " + min);
}
private static String max(int qian,int bai, int shi, int ge){
boolean bb = false; //用来判断数字是否改变
for (int i = 0; i < 4; i++) {
// 进入千位
if (qian == 1){ //添加火柴变为 7
if (ge != jian(ge)){ //当个位被改变时,则表示个位的数字可以减去一根火柴,变为其他合理的数字
ge = jian(ge); //覆盖原来个位的数字
qian=7; //改变千位上的数字为7
break;
}else if (shi != jian(shi)){ //当个位数字无法改变时,则判断十位上数字能否修改,以此类推
shi = jian(shi);
qian=7;
break;
}else if (bai != jian(bai)){
bai = jian(bai);
qian=7;
break;
}
bb = true;
}else if (qian == 2){ // 移动自身
qian = 3;
break;
}else if (qian == 3 || qian == 5){ // 添加火柴 变为9
if (ge != jian(ge)){
ge = jian(ge);
qian=9;
break;
}else if (shi != jian(shi)){
shi = jian(shi);
qian=9;
break;
}else if (bai != jian(bai)){
bai = jian(bai);
qian=9;
break;
}
bb = true;
}else if (qian == 6 || qian == 0){ // 移动自身变为9
qian = 9;
break;
}else if (qian == 8){ //减去火柴 变为9
if (bai != jia(bai)){ // 注意 此处优先级发生改变
bai = jia(bai);
qian=9;
break;
}else if (shi != jia(shi)){
shi = jia(shi);
qian=9;
break;
}else if (ge != jia(ge)){
ge = jia(ge);
qian=9;
break;
}
bb = true; // 千位未改变
}
// 进入百位
if (bb || qian == 4 || qian == 7 || qian == 9){ // 千位未改变,或无法改变
if (bai == 1){ //+7
if (ge != jian(ge)){
ge = jian(ge);
bai=7;
break;
}else if (shi != jian(shi)){
shi = jian(shi);
bai=7;
break;
}
bb = true;
}else if (bai == 2){
bai = 3;
break;
}else if (bai == 3 || bai == 5){ //+9
if (ge != jian(ge)){
ge = jian(ge);
bai=9;
break;
}else if (shi != jian(shi)){
shi = jian(shi);
bai=9;
break;
}
bb = true;
}else if (bai == 6 || bai == 0){
bai = 9;
break;
}else if (bai == 8){ //-9
if (shi != jia(shi)){
shi = jia(shi);
bai=9;
break;
}else if (ge != jia(ge)){
ge = jia(ge);
bai=9;
break;
}
bb = true;
}else if (bb || bai == 4 || bai == 7 || bai == 9){ // 进入十位
if (shi == 1){ //+7
if (ge != jian(ge)){
ge = jian(ge);
shi=7;
break;
}
bb = true;
}else if (shi == 2){
shi = 3;
break;
}else if (shi == 3 || shi == 5){ //+9
if (ge != jian(ge)){
ge = jian(ge);
shi=9;
break;
}
bb = true;
}else if (shi == 6 || shi == 0){
shi = 9;
break;
}else if (shi == 8){ //-9
if (ge != jia(ge)){
ge = jia(ge);
shi=9;
break;
}
bb = true;
}else if (bb || shi == 4 || shi == 7 || shi == 9){ // 进入个位
if (ge == 2){
ge = 3;
break;
}else if (ge == 6 || ge == 0){
ge = 9;
break;
}
break; // 均不能修改 则直接返回原数
}
}
}
}
return qian+""+bai+shi+ge;
}
private static int jian(int num){ //减去一根火柴,变为最大数
if (num == 6){
return 5;
}else if (num == 7){
return 1;
}else if (num == 8){
return 9;
}else if (num == 9){
return 5;
}
return num;
}
private static int jia(int num){ //增加一根火柴,变为最大数
if (num == 1){
return 7;
}else if (num == 3){
return 9;
}else if (num == 5){
return 9;
}else if (num == 6){
return 8;
}else if (num == 9){
return 8;
}else if (num == 0){
return 8;
}
return num;
}
最小数:
思路分析:
-
按减小优先级进行移动火柴,需要减少火柴也按照减小优先级进行移动火柴;除去
9
加上一根火柴可以变为8
,其他可增加火柴的大小都将变大,且9
可直接移动自身变为0
,故无需考虑增加火柴数字变小的情况。 -
最佳情况是直接将千位的数字变小,这样就生成的数便是最小的。
-
减小优先级:千位 > 百位 > 十位 > 个位
-
增大优先级:个位 > 十位 > 百位 > 千位
-
1
不可减小 -
2
不可减小 -
3
移动自身 变为2
-
4
不可减小 -
5
移动自身 变为3
-
6
移动自身 变为0
-
7
减去一横 变为1
-
8
减去一横 变为0
-
9
移动自身 变为0
-
0
为最小 无需改变
代码实现:
private static String min(int qian,int bai,int shi,int ge){
switch (qian){ //进入千位
case 3:
qian = 2;
break;
case 5:
qian = 3;
break;
case 6:
qian = 0;
break;
case 7:
if (bai !=jia1(bai)){
bai = jia1(bai);
qian = 1;
break;
}else if (shi != jia1(shi)){
shi = jia1(shi);
qian = 1;
break;
}else if (ge != jia1(ge)){
ge = jia1(ge);
qian = 1;
break;
}
case 8:
if (bai !=jia1(bai)){
bai = jia1(bai);
qian = 0;
break;
}else if (shi != jia1(shi)){
shi = jia1(shi);
qian = 0;
break;
}else if (ge != jia1(ge)){
ge = jia1(ge);
qian = 0;
break;
}
case 9:
qian = 0;
break;
default: // 千位未改变,或无法改变 则进入百位
switch (bai){
case 3:
bai = 2;
break;
case 5:
bai = 3;
break;
case 6:
bai = 0;
break;
case 7:
if (shi != jia1(shi)){
shi = jia1(shi);
bai = 1;
break;
}else if (ge != jia1(ge)){
ge = jia1(ge);
bai = 1;
break;
}
case 8:
if (shi != jia1(shi)){
shi = jia1(shi);
bai = 0;
break;
}else if (ge != jia1(ge)){
ge = jia1(ge);
bai = 0;
break;
}
case 9:
bai = 0;
break;
default: // 进入十位
switch (shi){
case 3:
shi = 2;
break;
case 5:
shi = 3;
break;
case 6:
shi = 0;
break;
case 7:
if (ge != jia1(ge)){
ge = jia1(ge);
shi = 1;
break;
}
case 8:
if (ge != jia1(ge)){
ge = jia1(ge);
shi = 0;
break;
}
case 9:
shi = 0;
break;
default: // 进入个位
switch (ge){
case 3:
shi = 2;
break;
case 5:
shi = 3;
break;
case 6:
shi = 0;
break;
case 9:
shi = 0;
break;
}
}
}
}
return qian+""+bai+shi+ge;
}
private static int jia1(int num){ //增加一根火柴,变为最小数
if (num == 1){
return 7;
}else if (num == 3){
return 9;
}else if (num == 5){
return 6;
}else if (num == 6 || num == 9 || num == 0){
return 8;
}
return num;
}