在Promela中选择语句比等效的if语句慢得多吗?

时间:2014-03-26 14:31:08

标签: spin model-checking promela

所以我在Promela代码中使用了以下行。

select( cycles: 26..31 );

然而,它导致了国家爆炸。我用下面的if语句替换了它,突然间状态爆炸问题消失了。上面显示的select语句不应该等同于下面的if语句吗?这是怎么回事?

if 
:: cycles = 26;
:: cycles = 27;
:: cycles = 28;
:: cycles = 29;
:: cycles = 30;
:: cycles = 31;
fi;

1 个答案:

答案 0 :(得分:4)

您的select语句由Spin转换为

cycles = 26;
do
  :: cycles < 31 -> cycles++
  :: break
od

这意味着在每个循环执行中有两种可供选择的可能性,即转换系统中的两种不同的后继状态。如果未选择break,则必须进行比较和分配(两个状态),然后继续。如果你想达到值31,你之前已经进行了5次比较和5次分配,而在if版本中,只有一个非确定性的选择。

我使用spinspider将两个不同版本可视化,这应该可以使问题更容易理解。

下图描绘了一个带有“if”-version的程序生成的状态空间,其中显然只有6种可供选择:

int cycles;

active proctype testWithIf() {
  if 
    :: cycles = 26;
    :: cycles = 27;
    :: cycles = 28;
    :: cycles = 29;
    :: cycles = 30;
    :: cycles = 31;
  fi;

  assert(cycles >= 26 && cycles <= 31);
}

State space from if-version

与此相比,将作为select语句转换为do-loop的程序生成的图像:

int cycles;
active proctype test1() {
  cycles = 26;
  do
    :: cycles < 31 -> cycles++
    :: break
  od;

  assert(cycles >= 26 && cycles <= 31);
}

State space from do/select version

你看到了差异吗?正如我所说,我认为主要的问题是,在if-version中你只需选择一个赋值,你必须在每个你不选择break的状态下做do-version中的多个事情:你必须做比较,递增计数器,然后继续。这显然会产生更大的状态空间。