postprocess: call restrict_dead_end_edges_here()

Related to issue #587.

* spot/twaalgos/postproc.cc, spot/twaalgos/postproc.hh: Add
support for option "rde".
* bin/spot-x.cc, NEWS: Mention it.
* tests/core/deadends.test, tests/core/ltl2tgba2.test,
tests/python/atva16-fig2a.ipynb, tests/python/deadends.py: Adjust test
cases to reflect the improvement.
* tests/core/ltlsynt.test: Also adjust this test case, which is the
only one worsened.  Some extra gates are generated when translating
GFa<->GFb with --algo=ds or --algo=sd.  Issue #588 would be one way to
fix that.
This commit is contained in:
Alexandre Duret-Lutz 2024-07-17 16:59:07 +02:00
parent 31511e042a
commit 6a7ef4db3f
9 changed files with 75 additions and 41 deletions

6
NEWS
View file

@ -6,7 +6,7 @@ New in spot 2.12.0.dev (not yet released)
edges leading to dead-ends. See the description of
restrict_dead_end_edges_here() below.
Library:
Library:
- restrict_dead_end_edges_here() can reduce non-determinism (but
not remove it) by restricting the label L of some edge (S)-L->(D)
@ -14,6 +14,10 @@ New in spot 2.12.0.dev (not yet released)
itself. The conditions are detailled in the documentation of
this function.
- spot::postprocessor will now call restrict_dead_end_edges_here()
in its highest setting. This can be fine-tuned with the "rde"
extra option, see the spot-x (7) man page for detail.
New in spot 2.12 (2024-05-16)
Build:

View file

@ -206,6 +206,12 @@ it can cause the created temporary automata to have incompatible \
combinations of atomic propositions that will be eventually be removed. \
This relabeling is attempted after relabel-bool. By default, N=8. Setting \
this value to 0 will disable the rewriting.") },
{ DOC("rde", "Disable (0), or enable (1) the 'restrict-dead-end-edges' \
optimization. A dead-end-edge is one that move to a state that has only \
itself as successors. The label of such edges can be simplified in some \
situtation, reducing non-determinism slightly. By default (-1), this is \
enabled only in --high mode, or if both --medium and --deterministic are \
used.") },
{ DOC("wdba-minimize", "Set to 0 to disable WDBA-minimization, to 1 to \
always try it, or 2 to attempt it only on syntactic obligations or on automata \
that are weak and deterministic. The default is 1 in --high mode, else 2 in \

View file

@ -38,6 +38,7 @@
#include <spot/twaalgos/parity.hh>
#include <spot/twaalgos/cobuchi.hh>
#include <spot/twaalgos/cleanacc.hh>
#include <spot/twaalgos/deadends.hh>
#include <spot/twaalgos/toparity.hh>
#include <spot/twaalgos/zlktree.hh>
@ -108,6 +109,7 @@ namespace spot
wdba_det_max_ = opt->get("wdba-det-max", 4096);
simul_trans_pruning_ = opt->get("simul-trans-pruning", 512);
acd_ = opt->get("acd", 1);
rde_ = opt->get("rde", -1);
if (sat_acc_ && sat_minimize_ == 0)
sat_minimize_ = 1; // Dicho.
@ -527,6 +529,14 @@ namespace spot
}
}
// Restricting dead-end edges only makes sense on non-deterministic
// automata. rde_ == 0 disable this. rde_ > 0 enable it.
// By default (rde_ < 0), we only enable this on High and Medium+Det.
if (!dba && rde_ != 0 && !is_deterministic(sim) &&
(rde_ > 0 || (level_ == High ||
(level_ == Medium && PREF_ == Deterministic))))
restrict_dead_end_edges_here(sim);
// If WDBA failed, but the simulation returned a deterministic
// automaton, use it as dba.
assert(dba || sim);

View file

@ -271,6 +271,7 @@ namespace spot
int wdba_det_max_ = 4096;
bool acd_ = true;
bool acd_was_used_;
int rde_ = -1;
};
/// @}
}

View file

@ -59,7 +59,8 @@ FG((Gp2 | Xp3) & (F!p2 | X!p3))
GFp0 & FGp1 & FGp2 & GFp3
EOF
ltl2tgba -F input.ltl | tee output.aut |
# disable rde so we can apply it manually
ltl2tgba -x rde=0 -F input.ltl | tee output.aut |
autfilt --restrict-dead --stats="%T %t %M" |
while read in out f; do
: $in : $out : "$f"
@ -68,3 +69,12 @@ ltl2tgba -F input.ltl | tee output.aut |
done
autcross -F output.aut --language-preserved 'autfilt --restrict-dead'
# by default, the result of ltl2tgba is already restricted
ltl2tgba -F input.ltl |
autfilt --restrict-dead --stats="%T %t %M" |
while read in out f; do
: $in : $out : "$f"
test $in -ne $out && exit 1
:
done

View file

@ -273,7 +273,7 @@ and-fg,32, $fg42, $fg42, $fg42, $fg42, $fg42, $fg42
!sb-patterns,5, 2,7, 2,7, 2,7, 2,7, 3,12, 3,12
!sb-patterns,6, 3,11, 4,14, 3,11, 4,14, 3,11, 4,14
!sb-patterns,7, 4,16, 4,16, 4,16, 4,16, 4,16, 4,16
!sb-patterns,9, 3,13, 3,13, 4,17, 4,17, 5,21, 5,21
!sb-patterns,9, 3,12, 3,12, 4,17, 4,17, 5,21, 5,21
!sb-patterns,10, 2,6, 2,6, 2,6, 2,6, 2,6, 2,6
!sb-patterns,11, 1,0, 1,0, 1,0, 1,0, 1,0, 1,0
!sb-patterns,12, 1,0, 1,0, 1,0, 1,0, 1,0, 1,0
@ -340,7 +340,7 @@ and-fg,32, $fg42, $fg42, $fg42, $fg42, $fg42, $fg42
!hkrss-patterns,53, 4,32, 4,32, 4,32, 4,32, 4,32, 4,32
!hkrss-patterns,54, 4,32, 4,32, 4,32, 4,32, 4,32, 4,32
!hkrss-patterns,55, 5,12, 6,12, 5,12, 6,12, 5,12, 6,12
!p-patterns,2, 2,15, 2,15, 3,19, 3,19, 4,23, 4,23
!p-patterns,2, 2,14, 2,14, 3,19, 3,19, 4,23, 4,23
!p-patterns,3, 3,41, 3,41, 3,41, 3,41, 3,41, 3,41
!p-patterns,4, 1,1, 1,1, 1,1, 1,1, 1,1, 1,1
!p-patterns,5, 2,6, 2,6, 2,6, 2,6, 2,6, 2,6
@ -379,7 +379,7 @@ FG(a | Fb), 3,15, 3,15, 3,15, 3,15, 1,4
FG(a & Fb), 2,7, 2,7, 3,9, 3,9, 1,4
GF(a & Gb), 2,7, 2,7, 3,9, 3,9, 1,4
GF(a | Gb), 2,7, 2,7, 3,12, 3,12, 1,4
Ge | GF(Ge & X(c & Fd)), 4,31, 4,31, 6,39, 6,39, 2,16
Ge | GF(Ge & X(c & Fd)), 4,30, 4,30, 6,39, 6,39, 2,16
F(GF(b & Gc) | Ge), 3,22, 3,22, 4,26, 4,26, 1,8
EOF

View file

@ -22,40 +22,43 @@
set -e
cat >exp <<EOF
parity 17;
0 1 0 7,8;
8 1 1 2;
parity 18;
0 2 0 7,8;
8 2 1 2;
2 3 0 11,12;
12 3 1 2,3;
3 2 0 13,14;
14 2 1 2,3;
13 2 1 1,4;
4 1 0 8,15;
15 1 1 5,6;
6 1 0 8,15;
5 2 0 16,17;
17 2 1 2;
16 2 1 5,6;
13 2 1 4,5;
5 2 0 8,17;
17 2 1 5,6;
6 1 0 10,18;
18 1 1 5,6;
10 1 1 2;
4 1 0 15,16;
16 1 1 2,3;
15 1 1 4,5;
11 3 1 4,5;
7 2 1 0,1;
1 1 0 9,10;
10 1 1 2,3;
9 1 1 1,5;
11 3 1 1,4;
7 1 1 1,2;
parity 13;
0 1 0 1,2;
9 1 1 0,1;
parity 15;
0 2 0 1,2;
2 1 1 3;
3 3 0 5,4;
4 2 1 12,3;
12 2 0 5,4;
5 1 1 6,7;
7 1 0 9,8;
8 3 1 12,3;
9 1 1 11,10;
10 2 0 9,8;
11 1 0 9,8;
6 1 0 13,4;
13 1 1 6,10;
1 1 1 6,3;
3 3 0 4,5;
5 2 1 6,3;
6 2 0 4,5;
4 1 1 7,8;
8 2 0 10,9;
9 3 1 6,3;
10 2 1 11,8;
11 1 0 12,9;
12 1 1 11,8;
7 1 0 13,5;
13 1 1 7,8;
1 2 1 14,0;
14 1 0 15,2;
15 1 1 14,0;
parity 5;
0 1 0 2,3;
3 3 1 1;

View file

@ -51,7 +51,7 @@
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\"?>\n",
"<!DOCTYPE svg PUBLIC \"-//W3C//DTD SVG 1.1//EN\"\n",
" \"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd\">\n",
"<!-- Generated by graphviz version 2.43.0 (0)\n",
"<!-- Generated by graphviz version 2.42.4 (0)\n",
" -->\n",
"<!-- Pages: 1 -->\n",
"<svg width=\"196pt\" height=\"355pt\"\n",
@ -95,7 +95,7 @@
"<title>0&#45;&gt;1</title>\n",
"<path fill=\"none\" stroke=\"black\" d=\"M72.76,-75.16C91.63,-83.74 123.36,-98.16 144.72,-107.87\"/>\n",
"<polygon fill=\"black\" stroke=\"black\" points=\"151.27,-110.85 143.59,-110.82 148.08,-109.4 144.9,-107.95 144.9,-107.95 144.9,-107.95 148.08,-109.4 146.2,-105.09 151.27,-110.85 151.27,-110.85\"/>\n",
"<text text-anchor=\"start\" x=\"99\" y=\"-104.8\" font-family=\"Lato\" font-size=\"14.00\">a | b</text>\n",
"<text text-anchor=\"start\" x=\"108.5\" y=\"-104.8\" font-family=\"Lato\" font-size=\"14.00\">a</text>\n",
"</g>\n",
"<!-- 2 -->\n",
"<g id=\"node4\" class=\"node\">\n",
@ -158,7 +158,7 @@
"<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\"?>\n",
"<!DOCTYPE svg PUBLIC \"-//W3C//DTD SVG 1.1//EN\"\n",
" \"http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd\">\n",
"<!-- Generated by graphviz version 2.43.0 (0)\n",
"<!-- Generated by graphviz version 2.42.4 (0)\n",
" -->\n",
"<!-- Pages: 1 -->\n",
"<svg width=\"196pt\" height=\"355pt\"\n",
@ -202,7 +202,7 @@
"<title>0&#45;&gt;1</title>\n",
"<path fill=\"none\" stroke=\"black\" d=\"M72.76,-75.16C91.63,-83.74 123.36,-98.16 144.72,-107.87\"/>\n",
"<polygon fill=\"black\" stroke=\"black\" points=\"151.27,-110.85 143.59,-110.82 148.08,-109.4 144.9,-107.95 144.9,-107.95 144.9,-107.95 148.08,-109.4 146.2,-105.09 151.27,-110.85 151.27,-110.85\"/>\n",
"<text text-anchor=\"start\" x=\"99\" y=\"-104.8\" font-family=\"Lato\" font-size=\"14.00\">a | b</text>\n",
"<text text-anchor=\"start\" x=\"108.5\" y=\"-104.8\" font-family=\"Lato\" font-size=\"14.00\">a</text>\n",
"</g>\n",
"<!-- 2 -->\n",
"<g id=\"node4\" class=\"node\">\n",
@ -262,7 +262,7 @@
"</svg>\n"
],
"text/plain": [
"<spot.twa_graph; proxy of <Swig Object of type 'std::shared_ptr< spot::twa_graph > *' at 0x7fdd801ca760> >"
"<spot.twa_graph; proxy of <Swig Object of type 'std::shared_ptr< spot::twa_graph > *' at 0x7f30b04c1d40> >"
]
},
"execution_count": 3,
@ -345,9 +345,9 @@
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.11.7"
"version": "3.12.4"
}
},
"nbformat": 4,
"nbformat_minor": 2
"nbformat_minor": 4
}

View file

@ -111,7 +111,7 @@ State: 1
[0&1&2] 1 {0 1}
--END--""")
a = spot.translate('GFa & (FGb | FGc) & GFc')
a = spot.translate('GFa & (FGb | FGc) & GFc', xargs='rde=0')
s = a.to_str()
spot.restrict_dead_end_edges_here(a)
s += a.to_str()