Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/dart/3.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 将项目指定给具有要素的组_Algorithm_Set_Combinations_Z3_Z3py - Fatal编程技术网

Algorithm 将项目指定给具有要素的组

Algorithm 将项目指定给具有要素的组,algorithm,set,combinations,z3,z3py,Algorithm,Set,Combinations,Z3,Z3py,我有一个问题,我是分配变量集。每个集合都有一个可以分配给它的变量限制,每个变量都可以分配给集合的某些子集 例如: a可以成套a或B b可以成套b c可以成套A或B d可以成套A 因此,我们可以有A:A,d;B:B,c或A:c,d;B:a,B(变量在集合中的顺序无关紧要) 我目前正在使用z3(在这里使用solve编写,也可以使用Solver表示)执行以下操作。根据下面的代码,如果a_in_a=True,则变量a处于设置a中 solve(If(a_in_B, 1, 0) + If(b_in_B,

我有一个问题,我是分配变量集。每个集合都有一个可以分配给它的变量限制,每个变量都可以分配给集合的某些子集

例如:

  • a
    可以成套
    a
    B
  • b
    可以成套
    b
  • c
    可以成套
    A
    B
  • d
    可以成套
    A
因此,我们可以有
A:A,d;B:B,c
A:c,d;B:a,B
(变量在集合中的顺序无关紧要)

我目前正在使用z3(在这里使用solve编写,也可以使用Solver表示)执行以下操作。根据下面的代码,如果
a_in_a=True
,则变量
a
处于设置
a

solve(If(a_in_B, 1, 0) + If(b_in_B, 1, 0) + If(c_in_B, 1, 0) <= 2,
      If(a_in_A, 1, 0) + If(c_in_A, 1, 0) + If(d_in_A, 1, 0) <= 2, 
      If(a_in_A, 1, 0) + If(a_in_B, 1, 0) == 1, 
      If(b_in_B, 1, 0) == 1, 
      If(c_in_A, 1, 0) + If(c_in_B, 1, 0) == 1, 
      If(d_in_A, 1, 0) == 1)

不过,我还想输入其他功能,如
c
必须在
a
之后设置。因此,我们将简化为
A:A,d;B:B,c
。如何将这些需求添加到z3解算器表达式中(或以其他方式添加)?

与任何编程任务一样,有许多方法可以解决此问题。我认为以下是z3py中最惯用的方法。注意内部
Set
类型的使用,它由数组在内部建模。我选择整数作为集合的元素,但如果愿意,可以将其设置为枚举类型(或其他一些基类型):

从z3导入*
s=解算器()
a、 b,c,d=Ints('abcd')
等位基因=[a,b,c,d]
s、 添加(不同的(等位基因))
#我们有两套
A、 B=Consts('ab',SetSort(IntSort()))
所有集合=[A,B]
#一般要求:每个元素都属于某个集合:
对于等位基因中的e:
属于=假;
对于所有集合中的x:
归属=或(归属,IsMember(e,x))
s、 添加(属于)
#容量要求
sizeA,sizeB=Ints('sizeA-sizeB'))
s、 添加(设置大小(A,sizeA))
s、 添加(设置大小(B,大小B))

s、 加(sizeA啊,这很有帮助!我困惑的一个部分是,我该如何使
问题特定要求
c必须在a的集合之后的集合中
扩展到多个集合和多个要求。我知道你在回答中提到了后者,但我似乎无法理解。对于前者,我该如何格式化多个“或”语句(以循环方式),使得每个变量能够覆盖多个集合(我假定“或”中只能有2个项)?
可以使用列表参数。我建议您尝试一下,如果卡住了,可以单独问一个关于堆栈溢出的特定问题,显示您尝试过的代码。此外,接受答案会告诉其他人问题已经解决。(请参阅答案旁边的“复选标记”)我在扩展你显示的代码时遇到了一些问题。我按照你的建议做了一个测试。我希望你能在回答这个问题时看一看,这样就有了背景。
solve(If(a_in_B, 4, 0) + If(b_in_B, 3, 0) + If(c_in_B, 3, 0) <= 6,
      If(a_in_A, 4, 0) + If(c_in_A, 3, 0) + If(d_in_A, 3, 0) <= 7, 
      If(a_in_A, 4, 0) + If(a_in_B, 4, 0) == 4, 
      If(b_in_B, 3, 0) == 3, 
      If(c_in_A, 3, 0) + If(c_in_B, 3, 0) == 3, 
      If(d_in_A, 3, 0) == 3)
s.add(Implies(IsMember(a, A), IsMember(c, B)))
s.add(Not(IsMember(a, B))) # otherwise there wouldn't be a place to put c!
[A = Lambda(k!0, Or(k!0 == 1, k!0 == 4)),
 b = 5,
 a = 1,
 d = 4,
 sizeB = 2,
 c = 3,
 sizeA = 2,
 B = Lambda(k!0, Or(k!0 == 3, k!0 == 5)),
 Ext = [else -> 5]]
a = 1
b = 5
c = 3
d = 4
A = Lambda(k!0, Or(k!0 == 1, k!0 == 4)),
B = Lambda(k!0, Or(k!0 == 3, k!0 == 5)),