Vcsn  2.0
Be Rational
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
wordset.hh
Go to the documentation of this file.
1 #ifndef VCSN_LABELSET_WORDSET_HH
2 # define VCSN_LABELSET_WORDSET_HH
3 
4 # include <memory>
5 # include <set>
6 
7 # include <boost/algorithm/string/predicate.hpp> // starts_with
8 
9 # include <vcsn/core/kind.hh>
10 # include <vcsn/labelset/fwd.hh>
12 # include <vcsn/labelset/labelset.hh>
13 # include <vcsn/misc/attributes.hh>
14 # include <vcsn/misc/hash.hh>
15 # include <vcsn/misc/raise.hh>
16 
17 namespace vcsn
18 {
20  template <typename GenSet>
21  class wordset: public detail::genset_labelset<GenSet>
22  {
23  public:
24  using genset_t = GenSet;
26  using self_type = wordset;
27  using genset_ptr = std::shared_ptr<const genset_t>;
28 
29  using letter_t = typename genset_t::letter_t;
30  using word_t = typename genset_t::word_t;
31  using letters_t = std::set<letter_t>;
32 
33  using value_t = word_t;
34 
36 
37  wordset(const genset_ptr& gs)
38  : super_t{gs}
39  {}
40 
41  wordset(const genset_t& gs = {})
42  : wordset{std::make_shared<const genset_t>(gs)}
43  {}
44 
45  static std::string sname()
46  {
47  return "wordset<" + super_t::sname() + ">";
48  }
49 
50  std::string vname(bool full = true) const
51  {
52  return "wordset<" + super_t::vname(full) + ">";
53  }
54 
56  static wordset make(std::istream& is)
57  {
58  // name: wordset<char(abc)>.
59  // ^^^^^^^ ^^^^^^^^^
60  // kind genset
61  eat(is, "wordset<");
62  auto gs = genset_t::make(is);
63  eat(is, ">");
64  return gs;
65  }
66 
70  bool open(bool o) const
71  {
72  return this->genset().open(o);
73  }
74 
75  static constexpr bool is_free()
76  {
77  return false;
78  }
79 
81  template <typename... Args>
82  value_t value(Args&&... args) const
83  {
84  return value_t{std::forward<Args>(args)...};
85  }
86 
88  word_t word(const value_t& v) const
89  {
90  return v;
91  }
92 
94  static word_t
96  {
97  return v;
98  }
99 
101  static bool
102  equals(const value_t l, const value_t r)
103  {
104  return l == r;
105  }
106 
108  static bool less_than(const value_t l, const value_t r)
109  {
110  return (std::forward_as_tuple(l.size(), l)
111  < std::forward_as_tuple(r.size(), r));
112  }
113 
114  static value_t
116  {
117  return genset_t::template special<value_t>();
118  }
119 
120  static bool
121  is_special(const value_t& v)
122  {
123  return v == special();
124  }
125 
126  bool
127  is_valid(const value_t& v) const
128  {
129  for (auto l: v)
130  if (!this->has(l))
131  return false;
132  return true;
133  }
134 
135  static constexpr bool
137  {
138  return false;
139  }
140 
141  static constexpr bool
143  {
144  return true;
145  }
146 
147  static constexpr bool
149  {
150  return false;
151  }
152 
153  static value_t
154  one()
155  {
156  return genset_t::empty_word();
157  }
158 
159  static bool
160  is_one(const value_t& l) ATTRIBUTE_PURE
161  {
162  return genset_t::is_empty_word(l);
163  }
164 
165  static size_t size(const value_t& v)
166  {
167  return v.length();
168  }
169 
170  static size_t hash(const value_t& v)
171  {
172  return hash_value(v);
173  }
174 
175  static value_t
177  {
178  return v;
179  }
180 
181  value_t
182  conv(std::istream& i) const
183  {
184  return this->genset().get_word(i);
185  }
186 
193  std::set<value_t>
194  convs(std::istream& i) const
195  {
196  std::set<value_t> res;
197  for (auto r : this->convs_(i))
198  res.insert(value_t{r});
199  return res;
200  }
201 
202  std::ostream&
203  print(const value_t& l, std::ostream& o,
204  symbol format = symbol{"text"}) const
205  {
206  if (is_one(l))
207  o << (format == "latex" ? "\\varepsilon" : "\\e");
208  else if (!is_special(l))
209  {
210  if (format == "latex" && ! this->is_letter(l))
211  o << "\\mathit{";
212  o << str_escape(l);
213  if (format == "latex" && ! this->is_letter(l))
214  o << "}";
215  }
216  return o;
217  }
218 
219  std::ostream&
220  print_set(std::ostream& o, symbol format = symbol{"text"}) const
221  {
222  if (format == "latex")
223  {
224  this->genset().print_set(o, format);
225  o << "^*";
226  }
227  else if (format == "text")
228  o << vname(true);
229  else
230  raise("invalid format: ", format);
231  return o;
232  }
233 
235  static value_t lgcd(const value_t& w1, const value_t& w2)
236  {
237  return {w1.begin(), std::mismatch(w1.begin(), w1.end(), w2.begin()).first};
238  }
239 
242  static value_t ldiv(const value_t& w1, const value_t& w2)
243  {
244  using boost::algorithm::starts_with;
245  require(starts_with(w2, w1), "ldiv: invalid arguments: ", str_escape(w1),
246  ", ", str_escape(w2));
247  return w2.substr(size(w1));
248  }
249 
251  static value_t& ldiv_here(const value_t& w1, value_t& w2)
252  {
253  w2 = ldiv(w1, w2);
254  return w2;
255  }
256  };
257 
258  namespace detail
259  {
261  template <typename GenSet>
262  struct nullableset_traits<wordset<GenSet>>
263  {
265  static type value(const wordset<GenSet>& ls)
266  {
267  return ls;
268  }
269  };
270 
271  template <typename GenSet>
272  struct law_traits<wordset<GenSet>>
273  {
275  static type value(const wordset<GenSet>& ls)
276  {
277  return ls;
278  }
279  };
280 
281  /*-------.
282  | Join. |
283  `-------*/
284 
286 #define DEFINE(Lhs, Rhs) \
287  template <typename GenSet> \
288  struct join_impl<Lhs, Rhs> \
289  { \
290  using type = Rhs; \
291  static type join(const Lhs& lhs, const Rhs& rhs) \
292  { \
293  return {get_union(lhs.genset(), rhs.genset())}; \
294  } \
295  }
296 
301 #undef DEFINE
302  }
303 
305  // FIXME: Factor in genset_labelset?
306  template <typename GenSet>
308  meet(const wordset<GenSet>& lhs, const wordset<GenSet>& rhs)
309  {
310  return {intersection(lhs.genset(), rhs.genset())};
311  }
312 }
313 
314 #endif // !VCSN_LABELSET_WORDSET_HH
static constexpr bool is_letterized()
Definition: wordset.hh:148
std::shared_ptr< const genset_t > genset_ptr
static bool equals(const value_t l, const value_t r)
Whether l == r.
Definition: wordset.hh:102
value_t conv(std::istream &i) const
Definition: wordset.hh:182
static value_t & ldiv_here(const value_t &w1, value_t &w2)
w2 := w1 \ w2.
Definition: wordset.hh:251
static value_t lgcd(const value_t &w1, const value_t &w2)
The longest common prefix.
Definition: wordset.hh:235
std::set< letter_t > letters_t
std::ostream & print_set(std::ostream &o, symbol format=symbol{"text"}) const
Definition: wordset.hh:220
bool open(bool o) const
Whether unknown letters should be added, or rejected.
Definition: wordset.hh:70
The LAW from a LAL.
Definition: labelset.hh:62
value_t value(Args &&...args) const
Value constructor.
Definition: wordset.hh:82
std::ostream & print(const value_t &l, std::ostream &o, symbol format=symbol{"text"}) const
Definition: wordset.hh:203
Implementation of labels are nullables (letter or empty).
Definition: fwd.hh:13
static type value(const wordset< GenSet > &ls)
Definition: wordset.hh:275
boost::flyweight< std::string, boost::flyweights::no_tracking > symbol
An internalized string.
Definition: symbol.hh:24
word_t word(const value_t &v) const
Convert to a word.
Definition: wordset.hh:88
typename genset_t::word_t word_t
std::ostream & str_escape(std::ostream &os, const std::string &str)
Output a string, escaping special characters.
Definition: escape.cc:43
static std::string sname()
Definition: wordset.hh:45
static constexpr bool is_ratexpset()
Definition: wordset.hh:136
static bool is_special(const value_t &v)
Definition: wordset.hh:121
This class has no modeling purpose, it only serves to factor code common to letterset, nullableset and wordset.
std::string vname(bool full=true) const
std::size_t hash_value(const T &v)
Definition: hash.hh:61
ATTRIBUTE_PURE auto is_letter(Args &&...args) const -> decltype(this->genset().is_letter(std::forward< Args >(args)...))
static value_t one()
Definition: wordset.hh:154
bool is_valid(const value_t &v) const
Definition: wordset.hh:127
static type value(const wordset< GenSet > &ls)
Definition: wordset.hh:265
static value_t ldiv(const value_t &w1, const value_t &w2)
Compute w1 \ w2 = w1^{-1}w2.
Definition: wordset.hh:242
static std::string sname()
static size_t hash(const value_t &v)
Definition: wordset.hh:170
#define DEFINE(Lhs, Rhs)
Declare that Lhs v Rhs => Rhs (on the union of alphabets).
Definition: wordset.hh:286
auto meet(const ratexpset< Ctx1 > &a, const ratexpset< Ctx2 > &b) -> ratexpset< meet_t< Ctx1, Ctx2 >>
The meet of two ratexpsets.
Definition: ratexpset.hh:480
std::istringstream is
The input stream: the specification to translate.
Definition: translate.cc:329
std::set< letter_t > convs_(std::istream &i) const
Read a range of letters.
wordset(const genset_t &gs={})
Definition: wordset.hh:41
static bool less_than(const value_t l, const value_t r)
Whether l < r.
Definition: wordset.hh:108
ATTRIBUTE_PURE auto has(Args &&...args) const -> decltype(this->genset().has(std::forward< Args >(args)...))
std::string vname(bool full=true) const
Definition: wordset.hh:50
Provide a variadic mul on top of a binary mul(), and one().
Definition: fwd.hh:36
std::set< T, Compare, Alloc > intersection(const std::set< T, Compare, Alloc > &set1, const std::set< T, Compare, Alloc > &set2)
The intersection of two sets.
static constexpr bool is_free()
Definition: wordset.hh:75
static wordset make(std::istream &is)
Build from the description in is.
Definition: wordset.hh:56
char eat(std::istream &is, char c)
Check lookahead character and advance.
Definition: stream.cc:37
static constexpr bool has_one()
Definition: wordset.hh:142
static value_t special()
Definition: wordset.hh:115
static value_t conv(self_type, value_t v)
Definition: wordset.hh:176
typename genset_t::letter_t letter_t
Implementation of labels are letters.
Definition: fwd.hh:9
Implementation of labels are words.
Definition: fwd.hh:24
word_t value_t
Definition: wordset.hh:33
static bool is_one(const value_t &l) ATTRIBUTE_PURE
Definition: wordset.hh:160
std::set< value_t > convs(std::istream &i) const
Read a range of labels.
Definition: wordset.hh:194
The smallest nullableset which includes LabelSet.
Definition: labelset.hh:22
wordset(const genset_ptr &gs)
Definition: wordset.hh:37
typename genset_t::word_t word_t
Definition: wordset.hh:30
const genset_t & genset() const
variadic_mul_mixin< detail::r_impl > r
Definition: fwd.hh:42
static size_t size(const value_t &v)
Definition: wordset.hh:165
void require(bool b, Args &&...args)
If b is not verified, raise an error with args as message.
Definition: raise.hh:39
static word_t letters_of(word_t v)
Prepare to iterate over the letters of v.
Definition: wordset.hh:95