美文网首页
枚举算法

枚举算法

作者: jiamjg | 来源:发表于2018-12-29 00:12 被阅读0次

枚举法的本质就是从所有候选答案中搜索正确的解,使用该算法需要满足两个条件:

  1. 可预先确定候选答案的数量。
  2. 候选答案的范围在求解之前必须有一个确定的集合。

填数游戏 (即 ABCDE * A = EEEEEE)

每个字母表示从0~9的一个整数,且不同字母之间代表的整数是不同的,要求找出这些字母表示的整数,使得算式成立。
这种类型的题目有两个特点:

  1. 无规律性,也就是我们没有办法按照一定的规律从众多的候选答案中找到正解。
  2. 有穷性,也就是说这种题目在计算量上总会有一个上界,要么在上界范围内即可得出正解,要么不存在正解。
字母 变量 变量范围
A i 1-9
B j 0-9
C k 0-9
D l 0-9
E r 1-9

然后穷举所有可能性,直到满足条件为止。

public class FindCalu {
    public static void main(String[] args) {
        for(int i=1;i<=9;i++) {
            for(int j=0;j<=9;j++) {
                for(int k=0;k<=9;k++) {
                    for(int l=0;l<=9;l++) {
                        for(int r=0;r<=9;r++) {
                            //计算的时候记得要用long型
                            long mul=i*10000+j*1000+k*100+l*10+r;
                            long res=r*111111;
                            if(mul*(long)i==res) {
                                System.out.println(mul+"*"+i+"="+res);
                            }
                        }
                    }
                }
            }
        }
    }
}

填运算符

5 5 5 5 5=5 (中间的空间填的是运算符)。
即通过加减乘除来等于相应的结果数。
注意:

  1. 除号后面的被除数一定不为0
  2. 乘除法的优先级比加减法的优先级高

分析:

  1. 先把已经计算过的结果存储到一个变量名为left中,准备和下一个数字进行运算(待运算的第一个数据存储到另一个变量名为right中)两个变量均为double型;
  2. 如果为加/减则为顺序计算:left = left +or- right;
    如果为乘除,则先计算当前乘除部分: right = *or/ num[下一个数据],作为下一个数字进行运算
    如果为除则下一个运算数据不能为0才能继续运算:if (i[当前] < 4 || num[下一个数据] != 0){……}; (注意)
  3. left初始值为0,right初始值为输入待运算的第一个数;
  4. 运算完之后筛选判断:if (left + right == result) 计数器自增,输出;如果全部结束计数器为零,则表示无所需结果;
import java.util.Scanner;
public class FindOper {
    public static void main(String[] args) {
        char oper[]=new char[]{' ','+','-','*','/'};  //操作符号,稍微注意一下
        int type[] = new int[5];  //存放操作符号顺序
        int flag=1;//1为正数,-1为负数
        double left,right;
        int count=0;
        int num[]=new int[6];
        Scanner input=new Scanner(System.in);
        for(int i=1;i<=5;i++) {
            num[i]=input.nextInt();
        }
        int result=input.nextInt();
        input.close();
        for(type[1]=1;type[1]<=4;type[1]++) {
            if(type[1]<4||num[2]!=0) {
                for(type[2]=1;type[2]<=4;type[2]++) {
                    if(type[2]<4||num[3]!=0) {
                        for(type[3]=1;type[3]<=4;type[3]++) {
                            if(type[3]<4||num[4]!=0) {
                                for(type[4]=1;type[4]<=4;type[4]++) {
                                    if(type[4]<4||num[5]!=0) {
                                        left=0;
                                        right=num[1];
                                        flag=1;
                                        for(int o=1;o<=4;o++) {
                                            switch(oper[type[o]]) {
                                                case '+':{
                                                    left=left+right*flag;
                                                    right=num[o+1];
                                                    flag=1;
                                                    break;
                                                }
                                                case '-':{
                                                    left=left+right*flag;
                                                    right=num[o+1];
                                                    flag=-1;
                                                    break;
                                                }
                                                case '*':{
                                                    right=right*num[o+1];
                                                    break;
                                                }
                                                case '/':{
                                                    right=right/num[o+1];
                                                    break;
                                                }
                                            }
                                        }
                                        if(left+flag*right==result) {
                                            count++;
                                            for(int a=1;a<=4;a++) {
                                                System.out.print(""+num[a]+oper[type[a]]);
                                            }
                                            System.out.print(num[5]+"="+result);
                                            System.out.println();
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
        if(count==0) {
            System.out.println("无!");
        }
    }
}

相关文章

  • 算法学习3_枚举

    枚举算法又称穷举算法枚举算法的核心思想 : 有序的尝试每一种可能 题一、 3 * 6528 = 3 * 8256 ...

  • 算法 | 枚举算法

    【算法思想】 利用计算机运算速度快的特点,对问题的所有可能答案一一列举,并逐一检验,符合条件的保留,不符合的丢弃。...

  • 2018-08-02

    php实现组合枚举算法 源码

  • 枚举算法

    枚举法:又称穷举法,是指从可能的集合中一一列举各个元素,用题目给定的约束条件判定哪些是无用的,哪些是有用的。能使命...

  • 枚举算法

    今天我们来讲一个万金油算法,这个算法可以解决所有的问题,它就是枚举法(穷举法)。 枚举算法是我们在日常中使用到的最...

  • 枚举算法

    枚举法的本质就是从所有候选答案中搜索正确的解,使用该算法需要满足两个条件: 可预先确定候选答案的数量。 候选答案的...

  • 枚举

    枚举 枚举算法又叫穷举算法。 基本思想是“有序地去尝试每一种可能”。例子:□□□+□□□=□□□,将数字1~9分别...

  • 在不确定图(uncertain graph)中结合Bron-Ke

    参考资料:MULE算法不确定图上的枚举算法研究Bron-Kerbosch算法视频介绍Bron-Kerbosch算法...

  • Swift - 递归枚举

    个人理解 递归枚举是拥有另一个枚举作为枚举成员关联值的枚举,实际上就是Swift中枚举关联值的特性和递归算法在Sw...

  • 回溯算法

    如何理解“回溯算法”? 回溯的处理思想,有点类似枚举搜索。我们枚举所有的解,找到满足期望的解。为了有规律地枚举所有...

网友评论

      本文标题:枚举算法

      本文链接:https://www.haomeiwen.com/subject/wzxslqtx.html