Commit 487cd01d authored by Alexandre Duret-Lutz's avatar Alexandre Duret-Lutz

c++11: introduce tgba::succ(s) to replace tgba::succ_iter(s).

| tgba_succ_iterator* i = aut->succ_iter(s);
| for (i->begin(); !i->done(); i->next())
|   {
|      // ...
|   }
| delete i;

becomes

| for (auto i: aut->succ(s))
|   {
|      // ...
|   }

hiding the begin()/done()/next() interface, taking care of the delete,
and allowing more optimization to come.

* src/tgba/succiter.hh, src/tgba/tgba.hh: Implement the above
new interface.
* iface/gspn/ssp.cc, src/dstarparse/nsa2tgba.cc,
src/saba/sabacomplementtgba.cc, src/tgba/tgbakvcomplement.cc,
src/tgba/tgbamask.cc, src/tgba/tgbasafracomplement.cc,
src/tgba/tgbatba.cc, src/tgbaalgos/compsusp.cc, src/tgbaalgos/cutscc.cc,
src/tgbaalgos/degen.cc, src/tgbaalgos/emptiness.cc,
src/tgbaalgos/isdet.cc, src/tgbaalgos/ltl2tgba_fm.cc,
src/tgbaalgos/minimize.cc, src/tgbaalgos/powerset.cc,
src/tgbaalgos/safety.cc, src/tgbaalgos/simulation.cc,
src/tgbaalgos/tau03.cc, src/tgbatest/explicit2.cc: Update for
loops.
parent f59773e3
// -*- coding: utf-8 -*-
// Copyright (C) 2008, 2011, 2013 Laboratoire de Recherche et
// Copyright (C) 2008, 2011, 2013, 2014 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// Copyright (C) 2003, 2004, 2005, 2006, 2007 Laboratoire
// d'Informatique de Paris 6 (LIP6), département Systèmes Répartis
......@@ -365,9 +365,7 @@ namespace spot
state** state_array = 0;
size_t size_states = 0;
tgba_succ_iterator* i = data_->operand->succ_iter(s->right());
for (i->first(); !i->done(); i->next())
for (auto i: data_->operand->succ(s))
{
all_conds_ = i->current_condition();
outside_ = !all_conds_;
......@@ -454,8 +452,6 @@ namespace spot
free(props_[j].prop[conj]);
free(props_[j].prop);
}
delete i;
return new tgba_succ_iterator_gspn_ssp(succ_tgba_, size_tgba_,
bdd_array, state_array,
size_states, props_,
......
// Copyright (C) 2013 Laboratoire de Recherche et Développement de
// Copyright (C) 2013, 2014 Laboratoire de Recherche et Développement de
// l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
......@@ -153,8 +153,7 @@ namespace spot
todo.pop_front();
int src = bs2num[s];
tgba_succ_iterator* i = a->succ_iter(a->get_state(s.s));
for (i->first(); !i->done(); i->next())
for (auto i: a->succ(a->get_state(s.s)))
{
int dlabel = label(a, i->current_state());
......@@ -216,7 +215,6 @@ namespace spot
t->condition = i->current_condition();
}
}
delete i;
}
......
// -*- coding: utf-8 -*-
// Copyright (C) 2009, 2010, 2011, 2012, 2013 Laboratoire de Recherche
// et Développement de l'Epita (LRDE).
// Copyright (C) 2009, 2010, 2011, 2012, 2013, 2014 Laboratoire de
// Recherche et Développement de l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
//
......@@ -208,17 +208,14 @@ namespace spot
{
// Get successors states.
bdd condition = it->first;
tgba_succ_iterator* iterator =
automaton_->succ_iter(origin_->get_state());
std::vector<shared_state> state_list;
for (iterator->first(); !iterator->done(); iterator->next())
{
bdd c = iterator->current_condition();
if ((c & condition) != bddfalse)
state_list.push_back(shared_state(iterator->current_state(),
shared_state_deleter));
}
delete iterator;
for (auto iterator: automaton_->succ(origin_->get_state()))
{
bdd c = iterator->current_condition();
if ((c & condition) != bddfalse)
state_list.push_back(shared_state(iterator->current_state(),
shared_state_deleter));
}
// Make the conjunction with ranks.
std::vector<int> current_ranks(state_list.size(), max_rank);
......@@ -292,14 +289,11 @@ namespace spot
std::set<int> atomics;
delete_condition_list();
tgba_succ_iterator* iterator =
automaton_->succ_iter(origin_->get_state());
for (iterator->first(); !iterator->done(); iterator->next())
for (auto iterator: automaton_->succ(origin_->get_state()))
{
bdd c = iterator->current_condition();
get_atomics(atomics, c);
}
delete iterator;
// Compute the conjunction of all those atomic properties.
unsigned atomics_size = atomics.size();
......
// -*- coding: utf-8 -*-
// Copyright (C) 2011, 2013 Laboratoire de Recherche et Developpement de
// l'Epita (LRDE).
// Copyright (C) 2011, 2013, 2014 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// Copyright (C) 2003, 2004, 2005 Laboratoire d'Informatique de Paris 6 (LIP6),
// département Systèmes Répartis Coopératifs (SRC), Université Pierre
// et Marie Curie.
......@@ -99,6 +99,73 @@ namespace spot
//@}
};
class tgba;
namespace internal
{
struct SPOT_API succ_iterator
{
protected:
tgba_succ_iterator* it_;
public:
succ_iterator(tgba_succ_iterator* it):
it_(it)
{
}
bool operator==(succ_iterator o) const
{
return it_ == o.it_;
}
bool operator!=(succ_iterator o) const
{
return it_ != o.it_;
}
const tgba_succ_iterator* operator*() const
{
return it_;
}
void operator++()
{
it_->next();
if (it_->done())
it_ = nullptr;
}
};
class SPOT_API succ_iterable
{
protected:
const tgba* aut_;
tgba_succ_iterator* it_;
public:
succ_iterable(const tgba* aut, tgba_succ_iterator* it)
: aut_(aut), it_(it)
{
}
~succ_iterable()
{
delete it_;
}
succ_iterator begin()
{
it_->first();
return it_->done() ? nullptr : it_;
}
succ_iterator end()
{
return nullptr;
}
};
}
}
......
// Copyright (C) 2009, 2011, 2013 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// -*- coding: utf-8 -*-
// Copyright (C) 2009, 2011, 2013, 2014 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// Copyright (C) 2003, 2004, 2005 Laboratoire d'Informatique de
// Paris 6 (LIP6), département Systèmes Répartis Coopératifs (SRC),
// Université Pierre et Marie Curie.
// Paris 6 (LIP6), département Systèmes Répartis Coopératifs (SRC),
// Université Pierre et Marie Curie.
//
// This file is part of Spot, a model checking library.
//
......@@ -23,12 +24,14 @@
# define SPOT_TGBA_TGBA_HH
#include "state.hh"
#include "succiter.hh"
#include "bdddict.hh"
#include "succiter.hh"
namespace spot
{
/// \defgroup tgba TGBA (Transition-based Generalized Büchi Automata)
class tgba_succ_iterator;
/// \defgroup tgba TGBA (Transition-based Generalized Büchi Automata)
///
/// Spot is centered around the spot::tgba type. This type and its
/// cousins are listed \ref tgba_essentials "here". This is an
......@@ -42,15 +45,15 @@ namespace spot
/// \ingroup tgba
/// \ingroup tgba_essentials
/// \brief A Transition-based Generalized Büchi Automaton.
/// \brief A Transition-based Generalized Büchi Automaton.
///
/// The acronym TGBA (Transition-based Generalized Büchi Automaton)
/// The acronym TGBA (Transition-based Generalized Büchi Automaton)
/// was coined by Dimitra Giannakopoulou and Flavio Lerda
/// in "From States to Transitions: Improving Translation of LTL
/// Formulae to Büchi Automata". (FORTE'02)
/// Formulae to Büchi Automata". (FORTE'02)
///
/// TGBAs are transition-based, meanings their labels are put
/// on arcs, not on nodes. They use Generalized Büchi acceptance
/// on arcs, not on nodes. They use Generalized Büchi acceptance
/// conditions: there are several acceptance sets (of
/// transitions), and a path can be accepted only if it traverses
/// at least one transition of each set infinitely often.
......@@ -105,8 +108,18 @@ namespace spot
/// product automaton. Otherwise, 0.
virtual tgba_succ_iterator*
succ_iter(const state* local_state,
const state* global_state = 0,
const tgba* global_automaton = 0) const = 0;
const state* global_state = nullptr,
const tgba* global_automaton = nullptr) const = 0;
/// \brief Build an iterable over the successors of \a s.
///
/// This is meant to be used as
/// <code>for (auto i: aut->out(s)) { /* i->current_state() */ }</code>.
internal::succ_iterable
succ(const state* s) const
{
return {this, succ_iter(s)};
}
/// \brief Get a formula that must hold whatever successor is taken.
///
......
// -*- coding: utf-8 -*-
// Copyright (C) 2009, 2010, 2011, 2013 Laboratoire de Recherche et
// Développement de l'Epita (LRDE).
// Copyright (C) 2009, 2010, 2011, 2013, 2014 Laboratoire de Recherche
// et Développement de l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
//
......@@ -325,13 +325,11 @@ namespace spot
i != sr_map.end();
++i)
{
tgba_succ_iterator* iterator = automaton_->succ_iter(i->first.get());
for (iterator->first(); !iterator->done(); iterator->next())
for (auto iterator: automaton_->succ(i->first.get()))
{
bdd c = iterator->current_condition();
get_atomics(atomics, c);
}
delete iterator;
}
// Compute the conjunction of all those atomic properties.
......@@ -433,8 +431,7 @@ namespace spot
i != sr_map.end();
++i)
{
tgba_succ_iterator* iterator = automaton_->succ_iter(i->first.get());
for (iterator->first(); !iterator->done(); iterator->next())
for (auto iterator: automaton_->succ(i->first.get()))
{
bdd c = iterator->current_condition();
if ((c & condition) != bddfalse)
......@@ -449,7 +446,6 @@ namespace spot
highest_current_ranks_[s] = i->second;
}
}
delete iterator;
}
// Highest $O$ set of the algorithm.
......@@ -460,8 +456,7 @@ namespace spot
i != s_set.end();
++i)
{
tgba_succ_iterator* iterator = automaton_->succ_iter(i->get());
for (iterator->first(); !iterator->done(); iterator->next())
for (auto iterator: automaton_->succ(i->get()))
{
bdd c = iterator->current_condition();
if ((c & condition) != bddfalse)
......@@ -470,7 +465,6 @@ namespace spot
highest_state_set_.insert(s);
}
}
delete iterator;
}
current_ranks_ = highest_current_ranks_;
......@@ -683,22 +677,18 @@ namespace spot
bdd
tgba_kv_complement::compute_support_conditions(const state* state) const
{
tgba_succ_iterator* i = succ_iter(state);
bdd result = bddtrue;
for (i->first(); !i->done(); i->next())
bdd result = bddfalse;
for (auto i: succ(state))
result |= i->current_condition();
delete i;
return result;
}
bdd
tgba_kv_complement::compute_support_variables(const state* state) const
{
tgba_succ_iterator* i = succ_iter(state);
bdd result = bddtrue;
for (i->first(); !i->done(); i->next())
for (auto i: succ(state))
result &= bdd_support(i->current_condition());
delete i;
return result;
}
......
// -*- coding: utf-8 -*-
// Copyright (C) 2013 Laboratoire de Recherche et Développement
// Copyright (C) 2013, 2014 Laboratoire de Recherche et Développement
// de l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
......@@ -36,8 +36,8 @@ namespace spot
{
~succ_iter_filtered()
{
for (first(); !done(); next())
it_->dest->destroy();
for (auto& t: trans_)
t.dest->destroy();
}
void first()
......@@ -138,15 +138,11 @@ namespace spot
tgba_succ_iterator*
tgba_mask::succ_iter(const state* local_state,
const state* global_state,
const tgba* global_automaton) const
const state*,
const tgba*) const
{
tgba_succ_iterator* it = original_->succ_iter(local_state,
global_state,
global_automaton);
succ_iter_filtered* res = new succ_iter_filtered;
for (it->first(); !it->done(); it->next())
for (auto it: original_->succ(local_state))
{
const state* s = it->current_state();
if (!wanted(s))
......@@ -159,7 +155,6 @@ namespace spot
it->current_acceptance_conditions() };
res->trans_.push_back(t);
}
delete it;
return res;
}
......
// -*- coding: utf-8 -*-
// Copyright (C) 2009, 2010, 2011, 2012, 2013 Laboratoire de Recherche
// et Développement de l'Epita (LRDE).
// Copyright (C) 2009, 2010, 2011, 2012, 2013, 2014 Laboratoire de
// Recherche et Développement de l'Epita (LRDE).
//
// This file is part of Spot, a model checking library.
//
......@@ -153,10 +153,9 @@ namespace spot
name = other.name;
parent = 0;
nodes = other.nodes;
for (child_list::const_iterator i = other.children.begin();
i != other.children.end(); ++i)
for (auto i: other.children)
{
safra_tree* c = new safra_tree(**i);
safra_tree* c = new safra_tree(*i);
c->parent = this;
children.push_back(c);
}
......@@ -170,11 +169,10 @@ namespace spot
safra_tree::~safra_tree()
{
for (child_list::iterator i = children.begin(); i != children.end(); ++i)
delete *i;
for (subset_t::iterator i = nodes.begin(); i != nodes.end(); ++i)
(*i)->destroy();
for (auto c: children)
delete c;
for (auto n: nodes)
n->destroy();
}
safra_tree&
......@@ -237,13 +235,10 @@ namespace spot
hash ^= wang32_hash(name);
hash ^= wang32_hash(marked);
for (subset_t::const_iterator i = nodes.begin(); i != nodes.end(); ++i)
hash ^= (*i)->hash();
for (child_list::const_iterator i = children.begin();
i != children.end();
++i)
hash ^= (*i)->hash();
for (auto n: nodes)
hash ^= n->hash();
for (auto c: children)
hash ^= c->hash();
return hash;
}
......@@ -262,13 +257,12 @@ namespace spot
safra_tree::max_name() const
{
int max_name = name;
for (child_list::const_iterator i = children.begin();
i != children.end(); ++i)
max_name = std::max(max_name, (*i)->max_name());
for (auto c: children)
max_name = std::max(max_name, c->max_name());
return max_name;
}
/// \brief Get an unused name in the tree for a new node.
/// \brief Get a unused name in the tree for a new node.
///
/// The root of the tree maintains a list of unused names.
/// When this list is empty, new names are computed.
......@@ -287,9 +281,8 @@ namespace spot
const safra_tree* current = queue.front();
queue.pop_front();
used_names.insert(current->name);
for (child_list::const_iterator i = current->children.begin();
i != current->children.end(); ++i)
queue.push_back(*i);
for (auto c: current->children)
queue.push_back(c);
}
int l = 0;
......@@ -325,13 +318,13 @@ namespace spot
safra_tree*
safra_tree::branch_accepting(const sba& a)
{
for (child_list::iterator i = children.begin(); i != children.end(); ++i)
(*i)->branch_accepting(a);
for (auto c: children)
c->branch_accepting(a);
subset_t subset;
for (subset_t::const_iterator i = nodes.begin(); i != nodes.end(); ++i)
if (a.state_is_accepting(*i))
subset.insert(*i);
for (auto n: nodes)
if (a.state_is_accepting(n))
subset.insert(n);
if (!subset.empty())
children.push_back(new safra_tree(subset, this, get_new_name()));
......@@ -354,22 +347,20 @@ namespace spot
{
subset_t new_subset;
for (subset_t::iterator i = nodes.begin(); i != nodes.end(); ++i)
for (auto n: nodes)
{
cache_t::const_iterator it = cache_transition.find(*i);
cache_t::const_iterator it = cache_transition.find(n);
if (it == cache_transition.end())
continue;
const tr_cache_t& transitions = it->second;
for (tr_cache_t::const_iterator t_it = transitions.begin();
t_it != transitions.end();
++t_it)
for (auto t: transitions)
{
if ((t_it->first & condition) != bddfalse)
if ((t.first & condition) != bddfalse)
{
if (new_subset.find(t_it->second) == new_subset.end())
if (new_subset.find(t.second) == new_subset.end())
{
const state* s = t_it->second->clone();
const state* s = t.second->clone();
new_subset.insert(s);
}
}
......@@ -377,8 +368,8 @@ namespace spot
}
nodes = new_subset;
for (child_list::iterator i = children.begin(); i != children.end(); ++i)
(*i)->succ_create(condition, cache_transition);
for (auto c: children)
c->succ_create(condition, cache_transition);
return this;
}
......@@ -391,18 +382,16 @@ namespace spot
safra_tree::normalize_siblings()
{
std::set<const state*, state_ptr_less_than> node_set;
for (child_list::iterator child_it = children.begin();
child_it != children.end();
++child_it)
for (auto c: children)
{
subset_t::iterator node_it = (*child_it)->nodes.begin();
while (node_it != (*child_it)->nodes.end())
subset_t::iterator node_it = c->nodes.begin();
while (node_it != c->nodes.end())
{
if (!node_set.insert(*node_it).second)
{
const state* s = *node_it;
(*child_it)->remove_node_from_children(*node_it);
(*child_it)->nodes.erase(node_it++);
c->remove_node_from_children(*node_it);
c->nodes.erase(node_it++);
s->destroy();
}
else
......@@ -411,7 +400,7 @@ namespace spot
}
}
(*child_it)->normalize_siblings();
c->normalize_siblings();
}
return this;
......@@ -421,18 +410,16 @@ namespace spot
void
safra_tree::remove_node_from_children(const state* state)
{
for (child_list::iterator child_it = children.begin();
child_it != children.end();
++child_it)
for (auto c: children)
{
subset_t::iterator it = (*child_it)->nodes.find(state);
if (it != (*child_it)->nodes.end())
subset_t::iterator it = c->nodes.find(state);
if (it != c->nodes.end())
{
const spot::state* s = *it;
(*child_it)->nodes.erase(it);
c->nodes.erase(it);
s->destroy();
}
(*child_it)->remove_node_from_children(state);
c->remove_node_from_children(state);
}
}
......@@ -470,12 +457,10 @@ namespace spot
safra_tree::mark()
{
std::set<const state*, state_ptr_less_than> node_set;
for (child_list::const_iterator child_it = children.begin();
child_it != children.end();
++child_it)
for (auto c: children)
{
node_set.insert((*child_it)->nodes.begin(), (*child_it)->nodes.end());
(*child_it)->mark();
node_set.insert(c->nodes.begin(), c->nodes.end());
c->mark();
}
char same = node_set.size() == nodes.size();
......@@ -500,10 +485,8 @@ namespace spot
if (same)
{
marked = true;
for (child_list::iterator i = children.begin();
i != children.end();
++i)
delete *i;
for (auto c: children)
delete c;
children = child_list();
}
......@@ -526,10 +509,8 @@ namespace spot
assert(bitset.size() > static_cast<unsigned>(name));
if (marked && !nodes.empty())
bitset.set(name);
for (child_list::const_iterator i = children.begin();
i != children.end();
++i)
(*i)->getL(bitset);
for (auto c: children)
c->getL(bitset);
}