Using set comprehension on binary relationships in Alloy

筅森魡賤 提交于 2019-12-24 03:02:07

问题


I have the following signatures:

sig Id, Grade {}

sig Foo {
    result : Id -> Grade
}

Now I want to create a function that takes in a foo variable and returns all associating Foo -> Grade relationships:

fun results[ id : Id ]: Foo -> Grade {
    //return all Foo->Grade binary relationships such that "id -> grade" in Foo.result
}

i.e.

So if the "result" relationship is like this:

(foo0, id0, grade0)
(foo0, id1, grade0)
(foo0, id2, grade1)
(foo1, id0, grade2)
(foo1, id3, grade3)
(foo2, id0, grade0)

and I run function "results[ id0 ]" I would get:

(foo0, grade0)
(foo1, grade2)
(foo2, grade0)

Now I guess I would use some sort of set comprehension, but the issue is that set comprehension only works with unary sets, not binary sets.


回答1:


Now i guess I would use some sort of set comprehension, but the issue is that set comprehension only works with unary sets, not binary sets.

Right the first time (yes, use set comprehension), not quite right the second (set comprehensions work fine with relations). See section B.8 of the language reference, or 3.5.5 of Software Abstractions.

Try something like this (not checked!):

fun results[ id : Id ]: Foo -> Grade {
/* return all Foo->Grade binary relationships
   such that "id -> grade" in Foo.result */
   { f : Foo, g : Grade 
     | f -> id -> g in result } 
   /* not Foo.result, that was a slip */
}

There may be a clever way to write the required set without a comprehension, just using box joins and dot joins, but if there is, at the moment it's eluding me. The closest I get is

{ f : Foo, g : Grade | f.result.g = id }


来源:https://stackoverflow.com/questions/28921494/using-set-comprehension-on-binary-relationships-in-alloy

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!