【问题标题】:N-Queens problem with adding the ordered constraint by using ortools使用 ortools 添加有序约束的 N-Queens 问题
【发布时间】:2020-11-25 16:16:32
【问题描述】:

我尝试使用本网站的代码进行一些练习。 https://developers.google.com/optimization/cp/queens

现在我想添加一些约束,使皇后的位置不在某些连续列之上升序(或降序)。 例如,设置board_size = 5。

(1) 满意的解决方案

问 _ _ _ _

_ _ 问 _ _

_ _ _ _ 问

_问_ _ _

_ _ _ 问 _

三个连续的列以上没有升序(或降序)。

(2) 降序

问 _ _ _ _

_ _ _ 问 _

_问_ _ _

_ _ _ _ 问

_ _ 问 _ _

column1 到column3 有一个降序排列。 (女王 1 > 女王 2 > 女王 3)

我添加了以下代码,但它不起作用。

for i in range(2, board_size):

  model.Add(queens[i - 2] <= queens[i - 1] <= queens[i])

如何更改代码以获得正确的约束,使皇后的位置不在某些列之上升序(或降序)?

更新: 这是我的问题代码。

class SolutionPrinter(cp_model.CpSolverSolutionCallback):
  """Print intermediate solutions."""

  def __init__(self, variables):
    cp_model.CpSolverSolutionCallback.__init__(self)
    self.__variables = variables
    self.__solution_count = 0

  def OnSolutionCallback(self):
    self.__solution_count += 1
    for v in self.__variables:
      print('%s = %i' % (v, self.Value(v)), end = ' ')
    print()

  def SolutionCount(self):
    return self.__solution_count

  board_size = 5
  model = cp_model.CpModel()
  # Creates the variables.
  # The array index is the column, and the value is the row.
  queens = [model.NewIntVar(0, board_size - 1, 'x%i' % i)
            for i in range(board_size)]
  # Creates the constraints.
  # The following sets the constraint that all queens are in different rows.
  model.AddAllDifferent(queens)

  # Note: all queens must be in different columns because the indices of queens are all different.

  # The following sets the constraint that no two queens can be on the same diagonal.
  for i in range(board_size):
    # Note: is not used in the inner loop.
    diag1 = []
    diag2 = []
    for j in range(board_size):
      # Create variable array for queens(j) + j.
      q1 = model.NewIntVar(0, 2 * board_size, 'diag1_%i' % i)
      diag1.append(q1)
      model.Add(q1 == queens[j] + j)
      # Create variable array for queens(j) - j.
      q2 = model.NewIntVar(-board_size, board_size, 'diag2_%i' % i)
      diag2.append(q2)
      model.Add(q2 == queens[j] - j)
    model.AddAllDifferent(diag1)
    model.AddAllDifferent(diag2)
  
  for i in range(2, board_size):
    model.Add(queens[i - 2] <= queens[i - 1])
    model.Add(queens[i - 1] <= queens[i])
  
  ### Solve model.
  solver = cp_model.CpSolver()
  solution_printer = SolutionPrinter(queens)
  status = solver.SearchForAllSolutions(model, solution_printer)
  print()
  print('Solutions found : %i' % solution_printer.SolutionCount())      

但它显示

找到的解决方案:0

.

【问题讨论】:

    标签: python or-tools


    【解决方案1】:

    添加两个不等式。

    model.Add(queens[i - 2] <= queens[i - 1])
    model.Add(queens[i - 1] <= queens[i])
    

    【讨论】:

    • 感谢您的回答!我尝试在我的代码中添加这两个不等式,但模型没有解决方案。
    • 你需要限制你的循环。没有解决方案将所有行之间的严格顺序。
    【解决方案2】:

    你尝试过使用引导吗?

    伪代码

    # Declare our intermediate boolean variable.
    b = [model.NewBoolVar('b') for i in range(board_size-2)]
    
    # Implement b[i] == (queens[i] < queens[i+1]).
    for i in range(board_size-2):
      model.Add(queens[i] < queens[i+1]).OnlyEnforceIf(b[i])
      model.Add(queens[i] > queens[i+1]).OnlyEnforceIf(b[i].Not())
    
      # Create our two half-reified constraints.
      # First, b[i] implies (queens[i+1] > queens[i+2]).
      model.Add(queens[i+1] > queens[i+2]).OnlyEnforceIf(b[i])
      # Second, not(b[i]) implies queens[i+1] < queens[i+2].
      model.Add(queens[i+1] < queens[i+2]).OnlyEnforceIf(b[i].Not())
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-11-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多