Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/algorithm/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Algorithm 如何找到具有线性约束的求和(xi)=b的所有整数解_Algorithm_Equation Solving_Integer Programming - Fatal编程技术网

Algorithm 如何找到具有线性约束的求和(xi)=b的所有整数解

Algorithm 如何找到具有线性约束的求和(xi)=b的所有整数解,algorithm,equation-solving,integer-programming,Algorithm,Equation Solving,Integer Programming,假设sum(xi)=10,0您正在寻找数字100的排列,其中每个整数分区 最多10个部件;及 每个零件最多15个 当然有很多案例,但是有10个!其中大部分仍由计算机管理 编辑:OP编辑了这个问题,所以:数字10应该分成最多10个部分的整数分区,每个部分最多2个。您正在寻找数字100的排列,其中每个整数分区都有 最多10个部件;及 每个零件最多15个 当然有很多案例,但是有10个!其中大部分仍由计算机管理 编辑:OP编辑了这个问题,所以:数字10应该被分解成最多10个部分的整数分区,每个部

假设sum(xi)=10,0您正在寻找数字100的排列,其中每个整数分区

  • 最多10个部件;及
  • 每个零件最多15个
当然有很多案例,但是有10个!其中大部分仍由计算机管理


编辑:OP编辑了这个问题,所以:数字10应该分成最多10个部分的整数分区,每个部分最多2个。

您正在寻找数字100的排列,其中每个整数分区都有

  • 最多10个部件;及
  • 每个零件最多15个
当然有很多案例,但是有10个!其中大部分仍由计算机管理


编辑:OP编辑了这个问题,所以:数字10应该被分解成最多10个部分的整数分区,每个部分最多2个。

如果你真的想得到所有的解决方案:递归地枚举所有可能的变量赋值,并进行一些优化:

  • 最后一个变量的值可以从sum约束计算出来
  • 当您看到部分赋值不能再导致有效的解决方案时(例如,如果总和已经大于10,或者如果剩下的变量太少,无法达到10的总和),可以删减搜索

  • 如果您真的想拥有所有解决方案:通过一些优化递归枚举所有可能的变量赋值:

  • 最后一个变量的值可以从sum约束计算出来
  • 当您看到部分赋值不能再导致有效的解决方案时(例如,如果总和已经大于10,或者如果剩下的变量太少,无法达到10的总和),可以删减搜索

  • 递归是最好的。以下是带有生成器的自然Python解决方案:

    def solutions(variables, sum_left, max_value):
        if 0 == variables:
            if 0 == sum_left:
                yield []
        else:
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    for partial_solution in solutions(variables - 1, sum_left - i,
                                                      max_value):
                        yield [i] + partial_solution
    
    for x in solutions(10, 10, 2):
        print(x)
    
    def解决方案(变量、左和、最大值):
    如果0==变量:
    如果0==左和_:
    收益率[]
    其他:
    对于范围内的i(0,最大值+1):
    如果sum_左
    生成器的好处是,您不必首先在内存中构建长列表。这里有一个替代解决方案,它不使用生成器,也避免了建立列表

    def do_something_for_solutions(variables, sum_left, max_value, known=None):
        if known is None:
            known = []
        if 0 == variables:
            if 0 == sum_left:
                do_something(known)
        else:
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    do_something_for_solutions(variables - 1, sum_left - i,
                                               max_value, known + [i])
    
    def do_something(solution):
        print(solution)
    
    do_something_for_solutions(10, 10, 2)
    
    def do_something_for_解决方案(变量、左和、最大值、已知=无):
    如果已知为无:
    已知=[]
    如果0==变量:
    如果0==左和_:
    做点什么(已知的)
    其他:
    对于范围内的i(0,最大值+1):
    如果sum_左
    如果您选择返回解决方案,可以按如下方式返回:

    def solutions(variables, sum_left, max_value):
        if 0 == variables:
            if 0 == sum_left:
                return [[]]
            else:
                return []
        else:
            answer = []
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    for partial_solution in solutions(variables - 1, sum_left - i,
                                                      max_value):
                        answer.append([i] + partial_solution)
            return answer
    
    for x in solutions(10, 10, 2):
        print(x)
    
    def解决方案(变量、左和、最大值):
    如果0==变量:
    如果0==左和_:
    返回[]]
    其他:
    返回[]
    其他:
    答案=[]
    对于范围内的i(0,最大值+1):
    如果sum_左

    (请注意,如果更改参数,该列表很容易变得庞大……

    递归是最好的。以下是带有生成器的自然Python解决方案:

    def solutions(variables, sum_left, max_value):
        if 0 == variables:
            if 0 == sum_left:
                yield []
        else:
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    for partial_solution in solutions(variables - 1, sum_left - i,
                                                      max_value):
                        yield [i] + partial_solution
    
    for x in solutions(10, 10, 2):
        print(x)
    
    def解决方案(变量、左和、最大值):
    如果0==变量:
    如果0==左和_:
    收益率[]
    其他:
    对于范围内的i(0,最大值+1):
    如果sum_左
    生成器的好处是,您不必首先在内存中构建长列表。这里有一个替代解决方案,它不使用生成器,也避免了建立列表

    def do_something_for_solutions(variables, sum_left, max_value, known=None):
        if known is None:
            known = []
        if 0 == variables:
            if 0 == sum_left:
                do_something(known)
        else:
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    do_something_for_solutions(variables - 1, sum_left - i,
                                               max_value, known + [i])
    
    def do_something(solution):
        print(solution)
    
    do_something_for_solutions(10, 10, 2)
    
    def do_something_for_解决方案(变量、左和、最大值、已知=无):
    如果已知为无:
    已知=[]
    如果0==变量:
    如果0==左和_:
    做点什么(已知的)
    其他:
    对于范围内的i(0,最大值+1):
    如果sum_左
    如果您选择返回解决方案,可以按如下方式返回:

    def solutions(variables, sum_left, max_value):
        if 0 == variables:
            if 0 == sum_left:
                return [[]]
            else:
                return []
        else:
            answer = []
            for i in range(0, max_value + 1):
                if sum_left < i:
                    break
                else:
                    for partial_solution in solutions(variables - 1, sum_left - i,
                                                      max_value):
                        answer.append([i] + partial_solution)
            return answer
    
    for x in solutions(10, 10, 2):
        print(x)
    
    def解决方案(变量、左和、最大值):
    如果0==变量:
    如果0==左和_:
    返回[]]
    其他:
    返回[]
    其他:
    答案=[]
    对于范围内的i(0,最大值+1):
    如果sum_左

    (请注意,如果您更改参数,该列表很容易变得庞大……

    示例中有太多解决方案,因此将它们全部列出是非常困难的