是否有更简单的方法来指定它?

时间:2014-08-21 14:41:51

标签: alloy

如下面的代码所示,有没有办法为表达式NP + NF2 + NF1 + NT + NRAnonActive + Aactive + AsetTurn + Astart + Acrit + Acheck + APF2 + APF1 + ATP + ATR + AF2R + AF1R制作宏,以便我可以稍后通过名称引用它们而不是直接写出表达式?< / p>

sig NP{}
sig NF2{}
sig NF1{}
sig NT{}
sig NR{}

sig AnonActive{src:one NP, trg:one NP}
sig Aactive{src:one NP, trg:one NP}
sig AsetTurn{src:one NP, trg:one NP}
sig Astart{src:one NP, trg:one NP}
sig Acrit{src:one NP, trg:one NP}
sig Acheck{src:one NP, trg:one NP}
sig APF2{src:one NP, trg:one NF2}
sig APF1{src:one NP, trg:one NF1}
sig ATP{src:one NT, trg:one NP}
sig ATR{src:one NT, trg:one NR}
sig AF2R{src:one NF2, trg:one NR}
sig AF1R{src:one NF1, trg:one NR}

sig Graph{nodes:set NP+NF2+NF1+NT+NR, 
          arrows:set AnonActive + Aactive + AsetTurn + Astart 
                     + Acrit + Acheck + APF2 + APF1 + ATP + ATR 
                     + AF2R + AF1R}

1 个答案:

答案 0 :(得分:1)

一种简单的方法是声明抽象签名NodeArrow,并将每个现有签名声明为扩展其中一个或另一个。

abstract sig Node {}
sig NP extends Node {}
sig NF2 extends Node {}
... 

由于所有箭头都具有相同的关系,因此可以在Arrow sig中声明关系;可以使用签名事实给出对源和目标允许的节点类型的限制,例如:

abstract sig Arrow {
  src:  one Node,
  trg:  one Node
}
sig AnonActive extends Arrow {}{
  one + trg in NP
}
...
sig AF1R extends Arrow {}{
  src in NF1
  trg in NR
}

现在Graph的声明很简单(至少对某些人而言,可能更清楚一点):

sig Graph {
  nodes: set Node,
  arrows: set Arrow 
}

另一种方法(我认为在所示情况下不太好,但在第一种方法无法应用的情况下很有用)将是用适当的名称定义函数:

fun Node : set univ {
  NP + NF2 + NF1 + NT + NR
}
fun Arrow : set univ {
  AnonActive + Aactive + AsetTurn + Astart 
  + Acrit + Acheck + APF2 + APF1 + ATP + ATR 
  + AF2R + AF1R
}

N.B。我没有检查这些语法错误...