Vcsn  2.4
Be Rational
tupleset.hh
Go to the documentation of this file.
1 #pragma once
2 
3 #include <array>
4 #include <iosfwd>
5 #include <istream>
6 #include <set>
7 #include <tuple>
8 
9 #include <boost/range/join.hpp>
10 #include <boost/optional.hpp>
11 
12 #include <vcsn/config.hh> // VCSN_HAVE_CORRECT_LIST_INITIALIZER_ORDER
13 //#include <vcsn/core/rat/expressionset.hh> needed, but breaks everythying...
14 #include <vcsn/labelset/fwd.hh>
16 #include <vcsn/misc/cross.hh>
17 #include <vcsn/misc/escape.hh>
18 #include <vcsn/misc/filter.hh>
19 #include <vcsn/misc/raise.hh>
20 #include <vcsn/misc/static-if.hh>
21 #include <vcsn/misc/stream.hh>
22 #include <vcsn/misc/tuple.hh> // tuple_element_t
23 #include <vcsn/misc/zip.hh>
24 #include <vcsn/weightset/b.hh>
25 
26 namespace vcsn
27 {
28  namespace detail
29  {
30 
35  template <typename Enable = void, typename... ValueSets>
37  {
38  using genset_t = void;
39  using genset_ptr = void;
40  using letter_t = void;
41  using letters_t = void;
43  using word_t = std::tuple<typename ValueSets::value_t...>;
44  constexpr static bool is_labelset = false;
45  };
46 
48  template <typename... ValueSets>
49  struct labelset_types_impl<decltype(pass{std::declval<ValueSets>().genset()...},
50  void()),
51  ValueSets...>
52  {
53  using genset_t
54  = cross_sequences<decltype(std::declval<ValueSets>().generators())...>;
55  using genset_ptr = std::tuple<typename ValueSets::genset_ptr...>;
56  using letter_t = std::tuple<typename ValueSets::letter_t...>;
57  using letters_t = std::set<letter_t,
58  vcsn::less<tupleset<ValueSets...>, letter_t>>;
59  using word_t = std::tuple<typename ValueSets::word_t...>;
60  constexpr static bool is_labelset = true;
61  };
62 
63  template <typename... ValueSets>
64  using labelset_types = labelset_types_impl<void, ValueSets...>;
65 
70  template <typename... ValueSets>
71  class tupleset_impl
72  {
73  public:
74  using valuesets_t = std::tuple<ValueSets...>;
75  using indices_t = make_index_sequence<sizeof...(ValueSets)>;
76  static constexpr indices_t indices{};
77  template <std::size_t... I>
78  using seq = index_sequence<I...>;
79 
81  template <std::size_t I>
83 
84  public:
85  using self_t = tupleset<ValueSets...>;
86 
88  using value_t = std::tuple<typename ValueSets::value_t...>;
89 
91  using letter_t = typename labelset_types<ValueSets...>::letter_t;
93  using letters_t = typename labelset_types<ValueSets...>::letters_t;
95  // using genset_t = typename labelset_types<ValueSets...>::genset_t;
96  using genset_ptr = typename labelset_types<ValueSets...>::genset_ptr;
98  using word_t = typename labelset_types<ValueSets...>::word_t;
99 
101  constexpr static bool is_labelset
102  = labelset_types<ValueSets...>::is_labelset;
103 
106 
108 
110  : sets_(std::move(vs))
111  {}
112 
113  tupleset_impl(ValueSets... ls)
114  : sets_(ls...)
115  {}
116 
117  static symbol sname()
118  {
119  static auto res = symbol{sname_(indices)};
120  return res;
121  }
122 
124  static constexpr std::size_t size()
125  {
126  return sizeof...(ValueSets);
127  }
128 
130  template <typename Value>
131  static size_t size(const Value& v)
132  {
133  return size_(v, indices);
134  }
135 
136  static constexpr bool
138  {
139  return is_commutative_(indices);
140  }
141 
142  static constexpr bool
144  {
145  return is_idempotent_(indices);
146  }
147 
149  static self_t make(std::istream& is)
150  {
151  // name: lat<law_char(abc), law_char(xyz)>
152  kind_t::make(is);
153  eat(is, '<');
154  auto res = make_(is, indices);
155  eat(is, '>');
156  return res;
157  }
158 
160  const valuesets_t& sets() const
161  {
162  return sets_;
163  }
164 
166  template <size_t I>
167  const valueset_t<I>& set() const
168  {
169  return std::get<I>(sets());
170  }
171 
173  template <size_t I>
175 
179  template <size_t I>
180  const valueset_t<I>& project() const
181  {
182  return set<I>();
183  }
184 
186  template <size_t I>
187  auto project(const value_t& v) const
188  {
189  return std::get<I>(v);
190  }
191 
195  bool open(bool o) const
196  {
197  return this->open_(o, indices);
198  }
199 
201  template <typename... Args>
202  value_t value(const std::tuple<Args...>& args) const
203  {
204  return this->value_(args, indices);
205  }
206 
208  template <typename... Args>
209  value_t tuple(Args&&... args) const
210  {
211  return value_t{args...};
212  }
213 
214  genset_ptr
215  genset() const
216  {
217  return this->genset_(indices);
218  }
219 
221  auto
222  generators() const
223  {
224  return this->generators_(indices);
225  }
226 
227  static constexpr bool is_free()
228  {
229  return is_free_(indices);
230  }
231 
233  template <typename... Args>
234  auto
235  word(const std::tuple<Args...>& v) const
236  -> word_t
237  {
238  return this->word_(v, indices);
239  }
240 
242  static bool
243  equal(const value_t& l, const value_t& r)
244  {
245  return equal_(l, r, indices);
246  }
247 
249  template <typename LhsValue, typename RhsValue>
250  static auto
251  less(const LhsValue& l, const RhsValue& r)
252  -> bool
253  {
254  auto sl = size(l);
255  auto sr = size(r);
256  if (sl < sr)
257  return true;
258  else if (sr < sl)
259  return false;
260  else
261  return less_(l, r, indices);
262  }
263 
264  static value_t
266  {
267  return special_(indices);
268  }
269 
270  static bool
271  is_special(const value_t& l)
272  {
273  return is_special_(l, indices);
274  }
275 
276  value_t
277  zero() const
278  {
279  return this->zero_(indices);
280  }
281 
282  bool
283  is_zero(const value_t& l) const
284  {
285  return is_zero_(l, indices);
286  }
287 
288  static constexpr bool
290  {
291  return has_lightening_weights_(indices);
292  }
293 
294  static constexpr bool
296  {
297  return has_one_(indices);
298  }
299 
300  static constexpr bool
302  {
303  return is_expressionset_(indices);
304  }
305 
306  static constexpr bool
308  {
309  return is_letterized_(indices);
310  }
311 
312  private:
313  template <std::size_t... I>
314  static auto one_(seq<I...>)
315  -> decltype(value_t{valueset_t<I>::one()...})
316  {
317  return value_t{valueset_t<I>::one()...};
318  }
319 
320  public:
325  template <typename Indices = indices_t>
326  static auto one() -> decltype(one_(Indices{}))
327  {
328  return one_(Indices{});
329  }
330 
331  static bool
332  is_one(const value_t& l)
333  {
334  return is_one_(l, indices);
335  }
336 
337  static bool
339  {
340  return show_one_(indices);
341  }
342 
343  bool
344  is_letter(const value_t&) const
345  {
346  // FIXME: why??? Is this for the printer of expressions?
347  return false;
348  }
349 
351  value_t
352  add(const value_t& l, const value_t& r) const
353  {
354  return map_(l, r,
355  [](const auto& vs, const auto& l, const auto& r)
356  {
357  return vs.add(l, r);
358  });
359  }
360 
365  template <typename LhsValue, typename RhsValue>
366  auto
367  mul(const LhsValue& l, const RhsValue& r) const
368  -> word_t
369  {
370  return this->mul_(l, r, indices);
371  }
372 
374  value_t
375  lgcd(const value_t& l, const value_t& r) const
376  {
377  return map_(l, r,
378  [](const auto& vs, const auto& l, const auto& r)
379  {
380  return vs.lgcd(l, r);
381  });
382  }
383 
385  value_t
386  rdivide(const value_t& l, const value_t& r) const
387  {
388  return map_(l, r,
389  [](const auto& vs, const auto& l, const auto& r)
390  {
391  return vs.rdivide(l, r);
392  });
393  }
394 
395  boost::optional<value_t>
396  maybe_rdivide(const value_t& l, const value_t& r) const
397  {
398  bool valid = true;
399  auto res = map_(l, r,
400  [&valid](const auto& vs, const auto& l, const auto& r)
401  {
402  if (auto res = vs.maybe_rdivide(l, r))
403  return *res;
404  else
405  {
406  valid = false;
407  return l;
408  }
409  });
410 
411  if (valid)
412  return res;
413  else
414  return boost::none;
415  }
416 
418  value_t
419  ldivide(const value_t& l, const value_t& r) const
420  {
421  return map_(l, r,
422  [](const auto& vs, const auto& l, const auto& r)
423  {
424  return vs.ldivide(l, r);
425  });
426  }
427 
428  boost::optional<value_t>
429  maybe_ldivide(const value_t& l, const value_t& r) const
430  {
431  bool valid = true;
432  auto res = map_(l, r,
433  [&valid](const auto& vs, const auto& l, const auto& r)
434  {
435  if (auto res = vs.maybe_ldivide(l, r))
436  return *res;
437  else
438  {
439  valid = false;
440  return l;
441  }
442  });
443 
444  if (valid)
445  return res;
446  else
447  return boost::none;
448  }
449 
454  typename valueset_t<0>::value_t
456  {
457  return this->lnormalize_here_(v, indices);
458  }
459 
461  value_t
462  star(const value_t& v) const
463  {
464  return map_(v,
465  [](const auto& vs, const auto& v)
466  {
467  return vs.star(v);
468  });
469  }
470 
476  template <typename Value>
477  Value
478  delimit(const Value& l) const
479  {
480  return this->delimit_(l, indices);
481  }
482 
484  template <typename Value>
485  Value
486  undelimit(const Value& l) const
487  {
488  return this->undelimit_(l, indices);
489  }
490 
491  // FIXME: this needs to be computed.
492  static constexpr star_status_t star_status()
493  {
495  }
496 
498  template <typename Value>
499  Value
500  transpose(const Value& l) const
501  {
502  return this->transpose_(l, indices);
503  }
504 
505  static size_t
506  hash(const value_t& v)
507  {
508  return hash_(v, indices);
509  }
510 
511  static value_t
513  {
514  return v;
515  }
516 
517  value_t
518  conv(b, b::value_t v) const
519  {
520  return v ? one() : zero();
521  }
522 
524  template <typename... VS>
525  value_t
527  const typename tupleset<VS...>::value_t& v) const
528  {
529  return this->conv_(vs, v, indices);
530  }
531 
533  template <typename... VS>
534  value_t
536  const typename nullableset<tupleset<VS...>>::value_t& v) const
537  {
538  return conv(*vs.labelset(), vs.get_value(v));
539  }
540 
542  value_t
543  conv(std::istream& i, bool quoted = true) const
544  {
545  constexpr auto has_label_one
546  = is_labelset && has_one_mem_fn<self_t>{};
547  return conv_(i, quoted, bool_constant<has_label_one>{});
548  }
549 
551  template <typename Fun>
552  void convs(std::istream& i, Fun&& fun) const
553  {
554  eat(i, '[');
555  conv_label_class_(*this, i,
556  [this,fun](const letter_t& l)
557  { fun(this->value(l)); });
558  eat(i, ']');
559  }
560 
561  std::ostream&
562  print_set(std::ostream& o, format fmt = {}) const
563  {
564  return this->print_set_(o, fmt, indices);
565  }
566 
567  std::ostream&
568  print(const value_t& l, std::ostream& o = std::cout,
569  format fmt = {}) const
570  {
571  return this->print_(l, o,
572  // 1, (2, 3) is different from 1, 2, 3:
573  // delimit components.
574  fmt.delimit(true),
575  fmt.delimit() ? "(" : "",
576  fmt.is_for_labels() ? "|" : ",",
577  fmt.delimit() ? ")" : "",
578  indices);
579  }
580 
581  private:
582  template <std::size_t... I>
583  static std::string sname_(seq<I...>)
584  {
585  std::string res = "lat<";
586  const char *sep = "";
587  for (auto n: {valueset_t<I>::sname()...})
588  {
589  res += sep;
590  res += n;
591  sep = ", ";
592  }
593  res.push_back('>');
594  return res;
595  }
596 
597  template <std::size_t... I>
598  static constexpr bool
600  {
601  return all_<valueset_t<I>::is_commutative()...>();
602  }
603 
604  template <std::size_t... I>
605  static constexpr bool
607  {
608  return all_<valueset_t<I>::is_idempotent()...>();
609  }
610 
611  template <std::size_t... I>
612  static self_t make_(std::istream& i, seq<I...>)
613  {
614 #if VCSN_HAVE_CORRECT_LIST_INITIALIZER_ORDER
615  return self_t{(eat_separator_<I>(i),
616  valueset_t<I>::make(i))...};
617 #else
618  return make_gcc_tuple
619  ((eat_separator_<sizeof...(ValueSets)-1 -I>(i),
620  valueset_t<sizeof...(ValueSets)-1 -I>::make(i))...);
621 #endif
622  }
623 
624  template <std::size_t... I>
625  bool open_(bool o, seq<I...>) const
626  {
627  using swallow = int[];
628  (void) swallow { set<I>().open(o)... };
629  std::swap(o, open__);
630  return o;
631  }
632 
635  template <typename Value, std::size_t I>
636  static auto size_(const Value& v, int)
637  -> decltype(valueset_t<I>::size(std::get<I>(v)))
638  {
639  return valueset_t<I>::size(std::get<I>(v));
640  }
641 
644  template <typename Value, std::size_t I>
645  static constexpr auto size_(const Value&, ...)
646  -> size_t
647  {
648  return 0;
649  }
650 
651  template <typename Value, std::size_t... I>
652  static size_t size_(const Value& v, seq<I...>)
653  {
654  return std::max({size_<Value, I>(v, 0)...});
655  }
656 
657  template <typename... Args, std::size_t... I>
658  value_t value_(const std::tuple<Args...>& args, seq<I...>) const
659  {
660  return value_t{set<I>().value(std::get<I>(args))...};
661  }
662 
663  template <std::size_t... I>
664  genset_ptr
666  {
667  return genset_ptr{set<I>().genset()...};
668  }
669 
670  template <std::size_t I>
671  decltype(auto) generators_() const
672  {
675  ([](const auto& ls)
676  {
677  using label_t = typename valueset_t<I>::value_t;
678  static const auto one = std::array<label_t, 1>{{ls.one()}};
679  return boost::range::join(one, ls.generators());
680  },
681  [](const auto& ls)
682  {
683  return ls.generators();
684  })(set<I>());
685  }
686 
687  template <std::size_t... I>
688  decltype(auto)
689  generators_(seq<I...>) const
690  {
691  // Need value(), since we might have to convert from letter_t to
692  // value_t.
693  auto p = [this](const auto& g)
694  { return !this->is_one(this->value(g)); };
695  return filter(vcsn::cross(generators_<I>()...),
696  // Need std::ref so that we can copy-assignment
697  // (filtered) iterators, which is needed with lat<lat<>>.
698  std::ref(p));
699  }
700 
701  template <std::size_t... I>
702  static constexpr bool
704  {
705  return all_<valueset_t<I>::is_free()...>();
706  }
707 
708  template <typename... Args, std::size_t... I>
709  word_t
710  word_(const std::tuple<Args...>& l, seq<I...>) const
711  {
712  return word_t{set<I>().word(std::get<I>(l))...};
713  }
714 
715  template <std::size_t... I>
716  static bool
717  equal_(const value_t& l, const value_t& r, seq<I...>)
718  {
719  for (auto n: {valueset_t<I>::equal(std::get<I>(l),
720  std::get<I>(r))...})
721  if (!n)
722  return false;
723  return true;
724  }
725 
726  template <typename LhsValue, typename RhsValue, std::size_t... I>
727  static auto
728  less_(const LhsValue& l, const RhsValue& r, seq<I...>)
729  -> bool
730  {
731  for (auto n: {std::make_pair(valueset_t<I>::less(std::get<I>(l),
732  std::get<I>(r)),
733  valueset_t<I>::less(std::get<I>(r),
734  std::get<I>(l)))...})
735  if (n.first)
736  return true;
737  else if (n.second)
738  return false;
739  return false;
740  }
741 
742  template <std::size_t... I>
743  static std::size_t
745  {
746  std::size_t res = 0;
747  for (auto h: {valueset_t<I>::hash(std::get<I>(v))...})
748  hash_combine(res, h);
749  return res;
750  }
751 
752  template <std::size_t... I>
753  static value_t
755  {
756  return std::make_tuple(valueset_t<I>::special()...);
757  }
758 
759  template <std::size_t... I>
760  static bool
762  {
763  for (auto n: {valueset_t<I>::is_special(std::get<I>(l))...})
764  if (!n)
765  return false;
766  return true;
767  }
768 
769  template <std::size_t... I>
770  value_t
772  {
773  return value_t{set<I>().zero()...};
774  }
775 
776  template <std::size_t... I>
777  bool
778  is_zero_(const value_t& l, seq<I...>) const
779  {
780  for (auto n: {set<I>().is_zero(std::get<I>(l))...})
781  if (!n)
782  return false;
783  return true;
784  }
785 
786  template <std::size_t... I>
787  static constexpr bool
789  {
790  return all_<valueset_t<I>::has_lightening_weights()...>();
791  }
792 
793  template <std::size_t... I>
794  static constexpr bool
796  {
797  return all_<valueset_t<I>::has_one()...>();
798  }
799 
800  template <std::size_t... I>
801  static constexpr bool
803  {
804  return all_<valueset_t<I>::is_expressionset()...>();
805  }
806 
807  template <std::size_t... I>
808  static constexpr bool
810  {
811  return all_<valueset_t<I>::is_letterized()...>();
812  }
813 
814  template <std::size_t... I>
815  static bool
817  {
818  for (auto n: {valueset_t<I>::is_one(std::get<I>(l))...})
819  if (!n)
820  return false;
821  return true;
822  }
823 
824  template <std::size_t... I>
825  static bool
827  {
828  for (auto n: {valueset_t<I>::show_one()...})
829  if (n)
830  return true;
831  return false;
832  }
833 
835  template <typename Fun>
836  value_t
837  map_(const value_t& v, Fun&& fun) const
838  {
839  return map_impl_(v, std::forward<Fun>(fun), indices);
840  }
841 
842  template <typename Fun, std::size_t... I>
843  value_t
844  map_impl_(const value_t& v, Fun&& fun, seq<I...>) const
845  {
846  return value_t{fun(set<I>(), std::get<I>(v))...};
847  }
848 
850  template <typename Fun>
851  value_t
852  map_(const value_t& l, const value_t& r, Fun&& fun) const
853  {
854  return map_impl_(l, r, std::forward<Fun>(fun), indices);
855  }
856 
857  template <typename Fun, std::size_t... I>
858  value_t
859  map_impl_(const value_t& l, const value_t& r, Fun&& fun, seq<I...>) const
860  {
861  return value_t{fun(set<I>(), std::get<I>(l), std::get<I>(r))...};
862  }
863 
864  template <typename LhsValue, typename RhsValue, std::size_t... I>
865  auto
866  mul_(const LhsValue& l, const RhsValue& r, seq<I...>) const
867  -> word_t
868  {
869  return word_t{set<I>().mul(std::get<I>(l), std::get<I>(r))...};
870  }
871 
872  template <std::size_t... I>
873  typename valueset_t<0>::value_t
875  {
876  typename valueset_t<0>::value_t res = std::get<0>(vs);
877  for (auto v: {std::get<I>(vs)...})
878  res = set<0>().lgcd(res, v);
879  using swallow = int[];
880  (void) swallow { (set<0>().ldivide_here(res, std::get<I>(vs)), 0)... };
881  return res;
882  }
883 
884  template <typename Value, std::size_t... I>
885  Value
886  delimit_(const Value& l, seq<I...>) const
887  {
888  return Value{set<I>().delimit(std::get<I>(l))...};
889  }
890 
891  template <typename Value, std::size_t... I>
892  Value
893  undelimit_(const Value& l, seq<I...>) const
894  {
895  return Value{set<I>().undelimit(std::get<I>(l))...};
896  }
897 
898  template <typename... VS, std::size_t... I>
899  value_t
901  const typename tupleset<VS...>::value_t& v,
902  seq<I...>) const
903  {
904  return value_t{set<I>().conv(vs.template set<I>(), std::get<I>(v))...};
905  }
906 
909  value_t
910  conv_(std::istream& i, bool quoted, std::true_type) const
911  {
912  if (i.peek() == EOF)
913  return one();
914  else
915  // This is not the empty string, bounce to the regular case.
916  return conv_(i, quoted, std::false_type{});
917  }
918 
920  value_t
921  conv_(std::istream& i, bool quoted, std::false_type) const
922  {
923  bool par = i.peek() == '(';
924  if (par)
925  eat(i, '(');
926  value_t res = conv_(i, quoted, indices);
927  if (par)
928  eat(i, ')');
929  return res;
930  }
931 
932  template <std::size_t... I>
933  value_t
934  conv_(std::istream& i, bool quoted, seq<I...>) const
935  {
936 #if VCSN_HAVE_CORRECT_LIST_INITIALIZER_ORDER
937  return value_t{(eat_separator_<I>(i),
938  set<I>().conv(i, quoted))...};
939 #else
940  constexpr auto S = sizeof...(ValueSets)-1;
941  return
942  detail::make_gcc_tuple((eat_separator_<S - I>(i),
943  set<S - I>().conv(i, quoted))...);
944 #endif
945  }
946 
951  template <std::size_t I>
952  static void
953  eat_separator_(std::istream& i)
954  {
955  if (I)
956  eat(i, i.peek() == ',' ? ',' : '|');
957  while (isspace(i.peek()))
958  i.ignore();
959  }
960 
961 
962  template <std::size_t... I>
963  std::ostream&
964  print_(const value_t& l, std::ostream& o,
965  format fmt,
966  const char* pre,
967  const char* sep,
968  const char* post,
969  seq<I...>) const
970  {
971  if (!is_special(l))
972  {
973  using swallow = int[];
974  (void) swallow
975  {
976  (o << (I == 0 ? pre : sep),
977  set<I>().print(std::get<I>(l), o, fmt),
978  0)...
979  };
980  o << post;
981  }
982  return o;
983  }
984 
985  template <std::size_t... I>
986  std::ostream&
987  print_set_(std::ostream& o, format fmt,
988  seq<I...>) const
989  {
990  const char *sep = "";
991  const char *close = "";
992  switch (fmt.kind())
993  {
994  case format::latex:
995  sep = " \\times ";
996  break;
997  case format::sname:
998  o << "lat<";
999  sep = ", ";
1000  close = ">";
1001  break;
1002  case format::text:
1003  sep = " x ";
1004  break;
1005  case format::utf8:
1006  sep = " × ";
1007  break;
1008  case format::raw:
1009  assert(0);
1010  break;
1011  }
1012  using swallow = int[];
1013  (void) swallow
1014  {
1015  (o << (I == 0 ? "" : sep),
1016  set<I>().print_set(o, fmt),
1017  0)...
1018  };
1019  o << close;
1020  return o;
1021  }
1022 
1023  template <typename Value, std::size_t... I>
1024  Value
1025  transpose_(const Value& l, seq<I...>) const
1026  {
1027  return Value{set<I>().transpose(std::get<I>(l))...};
1028  }
1029 
1031  template <std::size_t... I>
1032  self_t
1033  meet_(const self_t& rhs, seq<I...>) const
1034  {
1035  return self_t{meet(set<I>(), rhs.template set<I>())...};
1036  }
1037 
1039  friend
1040  self_t
1041  meet(const self_t& lhs, const self_t& rhs)
1042  {
1043  return lhs.meet_(rhs, indices);
1044  }
1045 
1047  friend
1048  self_t
1049  meet(const self_t& lhs, const b&)
1050  {
1051  return lhs;
1052  }
1053 
1055  friend
1056  self_t
1057  meet(const b&, const self_t& rhs)
1058  {
1059  return rhs;
1060  }
1061 
1065  mutable bool open__ = false;
1066 
1067  private:
1069  template <std::size_t... I>
1070  auto
1071  get_letter_(std::istream& i, bool quoted, seq<I...>) const
1072  -> letter_t
1073  {
1074 #if VCSN_HAVE_CORRECT_LIST_INITIALIZER_ORDER
1075  return letter_t{(eat_separator_<I>(i),
1076  set<I>().get_letter(i, quoted))...};
1077 #else
1078  constexpr auto S = sizeof...(ValueSets)-1;
1079  return
1080  detail::make_gcc_tuple((eat_separator_<S - I>(i),
1081  set<S - I>().get_letter(i, quoted))...);
1082 #endif
1083  }
1084 
1086  template <typename Value, std::size_t... I>
1087  static auto
1088  letters_of_(const Value& v, seq<I...>)
1089  -> decltype(zip(valueset_t<I>::letters_of(std::get<I>(v))...))
1090  {
1091  return zip(valueset_t<I>::letters_of(std::get<I>(v))...);
1092  }
1093 
1095  template <typename Value, typename... Defaults, std::size_t... I>
1096  auto
1097  letters_of_padded_(const Value& v,
1098  const std::tuple<Defaults...>& def, seq<I...>) const
1099  -> decltype(zip_with_padding(def,
1100  this->set<I>().letters_of_padded(std::get<I>(v),
1101  std::get<I>(def))...))
1102  {
1103  return zip_with_padding(def,
1104  set<I>().letters_of_padded(std::get<I>(v),
1105  std::get<I>(def))...);
1106  }
1107 
1108  public:
1109  template <std::size_t... I>
1110  auto
1111  get_letter(std::istream& i, bool quoted = true) const
1112  -> decltype(this->get_letter_(i, quoted, indices))
1113  {
1114  bool par = i.peek() == '(';
1115  if (par)
1116  eat(i, '(');
1117  auto res = get_letter_(i, quoted, indices);
1118  if (par)
1119  eat(i, ')');
1120  return res;
1121  }
1122 
1128  template <typename Value>
1129  static auto
1130  letters_of(const Value& v)
1131  -> decltype(letters_of_(v, indices))
1132  {
1133  return letters_of_(v, indices);
1134  }
1135 
1141  template <typename Value, typename... Defaults>
1142  auto
1143  letters_of_padded(const Value& v, const std::tuple<Defaults...>& def) const
1144  -> decltype(this->letters_of_padded_(v, def, indices))
1145  {
1146  return letters_of_padded_(v, def, indices);
1147  }
1148  };
1149 
1150  template <typename... ValueSets>
1151  tupleset<ValueSets...>
1152  make_tupleset(const ValueSets&... vss)
1153  {
1154  return {vss...};
1155  }
1156 
1157 
1158  /*----------------.
1159  | is_multitape. |
1160  `----------------*/
1161 
1163  template <typename ValueSet>
1165  : std::false_type
1166  {};
1167 
1168  template <typename... ValueSet>
1169  struct is_multitape<tupleset<ValueSet...>>
1170  : std::true_type
1171  {};
1172 
1173  template <typename LabelSet, typename WeightSet>
1174  struct is_multitape<context<LabelSet, WeightSet>>
1175  : is_multitape<LabelSet>
1176  {};
1177 
1178  template <typename Context>
1179  struct is_multitape<expressionset<Context>>
1180  : is_multitape<Context>
1181  {};
1182 
1183 
1184 
1185  template <typename T1, typename T2>
1187 
1188  // Sure, we'd like to use tuple<> instead of
1189  // weightset_mixin<tupleset_impl<>>, however then we hit a Clang
1190  // 3.5.0 bug.
1191  //
1192  // https://llvm.org/bugs/show_bug.cgi?id=19372
1193  template <typename... T1, typename... T2>
1196  {
1197  using type = weightset_mixin<tupleset_impl<T1..., T2...>>;
1198  };
1199 
1201  template <typename... LabelSets>
1202  struct letterized_traits<tupleset<LabelSets...>>
1203  {
1204  using indices_t = make_index_sequence<sizeof...(LabelSets)>;
1205 
1206  template <std::size_t... I>
1207  using seq = index_sequence<I...>;
1208 
1209  template <size_t I>
1210  using letterized_traits_t =
1212  template <std::size_t... I>
1213  static constexpr bool is_letterized_(seq<I...>)
1214  {
1216  }
1217  static constexpr bool is_letterized = is_letterized_(indices_t{});
1218 
1219  using labelset_t =
1221 
1222  static labelset_t labelset(const tupleset<LabelSets...>& ls)
1223  {
1224  return labelset_(ls, indices_t{});
1225  }
1226 
1227  template <std::size_t... I>
1228  static labelset_t labelset_(const tupleset<LabelSets...>& ls,
1229  seq<I...>)
1230  {
1231  return {make_letterized(std::get<I>(ls.sets()))...};
1232  }
1233  };
1234 
1236  template <typename... LabelSets>
1237  struct nullableset_traits<tupleset<LabelSets...>,
1238  std::enable_if_t<tupleset<LabelSets...>::has_one()>>
1239  {
1240  using labelset_t = tupleset<LabelSets...>;
1241  using type = labelset_t;
1242  static type value(const labelset_t& ls)
1243  {
1244  return ls;
1245  }
1246  };
1247 
1249  template <typename... LabelSets>
1250  struct nullableset_traits<tupleset<LabelSets...>,
1251  std::enable_if_t<!tupleset<LabelSets...>::has_one()>>
1252  {
1253  using labelset_t = tupleset<LabelSets...>;
1255 
1256  static type value(const labelset_t& ls)
1257  {
1258  return ls;
1259  }
1260  };
1261 
1263  template <typename LabelSet>
1264  struct proper_traits<tupleset<LabelSet>>
1265  {
1267  static type value(const tupleset<LabelSet>& ls)
1268  {
1269  return {proper_traits<LabelSet>::value(ls.template set<0>())};
1270  }
1271  };
1272 
1274  template <typename... LabelSets>
1275  struct law_traits<tupleset<LabelSets...>>
1276  {
1277  using labelset_t = tupleset<LabelSets...>;
1279 
1280  template <std::size_t... I>
1282  {
1283  return {make_wordset(ls.template set<I>())...};
1284  }
1285 
1286  static type value(const labelset_t& ls)
1287  {
1288  return value(ls, make_index_sequence<sizeof...(LabelSets)>{});
1289  }
1290  };
1291 
1293  template <typename... VS1, typename... VS2>
1294  struct join_impl<tupleset<VS1...>, tupleset<VS2...>>
1295  {
1296  static_assert(sizeof...(VS1) == sizeof...(VS2),
1297  "join: tuplesets must have the same sizes");
1298  using vs1_t = tupleset<VS1...>;
1299  using vs2_t = tupleset<VS2...>;
1302 
1303  template <std::size_t... I>
1304  static type join(const vs1_t& lhs, const vs2_t& rhs,
1306  {
1307  return {::vcsn::join(lhs.template set<I>(), rhs.template set<I>())...};
1308  }
1309 
1311  static type join(const vs1_t& lhs, const vs2_t& rhs)
1312  {
1313  return join(lhs, rhs,
1314  make_index_sequence<sizeof...(VS1)>{});
1315  }
1316  };
1317 
1319  template <typename... VS1, typename VS2>
1320  struct join_impl<tupleset<VS1...>, VS2>
1321  {
1322  // Cannot just leave "false" as condition: the assertion is then
1323  // always checked, even if the template is not instantiated.
1324  static_assert(is_multitape<VS2>{},
1325  "join: cannot mix tuplesets and non tuplesets");
1326  };
1327 
1328 
1329  /*------------------.
1330  | project_labelset. |
1331  `------------------*/
1332 
1335  template <size_t Tape, typename LabelSet>
1337 
1340  template <size_t Tape, typename LabelSet>
1342 
1344  template <size_t Tape, typename... LabelSets>
1345  struct project_labelset_impl<Tape, tupleset<LabelSets...>>
1346  {
1347  using valueset_t = tupleset<LabelSets...>;
1348  using type = typename valueset_t::template project_t<Tape>;
1349  };
1350 
1352  template <size_t Tape, typename Context>
1353  struct project_labelset_impl<Tape, expressionset<Context>>
1354  {
1356  using type = typename valueset_t::template project_t<Tape>;
1357  };
1358 
1359 
1360  /*------------------.
1361  | project_context. |
1362  `------------------*/
1363 
1365  template <size_t Tape, typename Context>
1366  using project_context
1369 
1370  }// detail::
1371 
1372 
1373  /*----------------.
1374  | random_label. |
1375  `----------------*/
1376 
1378  template <typename... LabelSet,
1379  typename RandomGenerator = std::default_random_engine>
1380  typename tupleset<LabelSet...>::value_t
1382  RandomGenerator& gen = RandomGenerator())
1383  {
1384  return random_label_(ls, gen, ls.indices);
1385  }
1386 
1387 
1389  template <typename... LabelSet,
1390  size_t... I,
1391  typename RandomGenerator = std::default_random_engine>
1392  typename tupleset<LabelSet...>::value_t
1394  RandomGenerator& gen,
1396  {
1397  // No need to check for the emptiness here: it will be checked in
1398  // each sub-labelset.
1399  return ls.tuple(random_label(ls.template set<I>(), gen)...);
1400  }
1401 
1402 
1403 }// vcsn::
typename labelset_types< ValueSets... >::word_t word_t
A tuple of words if meaningful, void otherwise.
Definition: tupleset.hh:98
value_t value_(const std::tuple< Args... > &args, seq< I... >) const
Definition: tupleset.hh:658
constant< type_t::one, Context > one
Definition: fwd.hh:113
STL namespace.
static bool equal(const value_t &l, const value_t &r)
Whether l equals r.
Definition: tupleset.hh:243
static bool is_special(const value_t &l)
Definition: tupleset.hh:271
value_t add(const value_t &l, const value_t &r) const
Pointwise addition.
Definition: tupleset.hh:352
static constexpr bool is_expressionset()
Definition: tupleset.hh:301
Print as is. For instance, don't try to escape labels.
Definition: format.hh:24
static value_t special()
Definition: tupleset.hh:265
static constexpr bool has_lightening_weights_(seq< I... >)
Definition: tupleset.hh:788
value_t conv(b, b::value_t v) const
Definition: tupleset.hh:518
char eat(std::istream &is, char c)
Check lookahead character and advance.
Definition: stream.cc:90
Print as a parsable type string.
Definition: format.hh:26
letter_t value_type
To be iterable.
Definition: tupleset.hh:105
value_t conv(const nullableset< tupleset< VS... >> &vs, const typename nullableset< tupleset< VS... >>::value_t &v) const
Convert a value from nullableset> to value_t.
Definition: tupleset.hh:535
static constexpr bool is_commutative_(seq< I... >)
Definition: tupleset.hh:599
friend self_t meet(const b &, const self_t &rhs)
The meet with the B weightset.
Definition: tupleset.hh:1057
std::tuple< ValueSets... > valuesets_t
Definition: tupleset.hh:74
auto mul(const LhsValue &l, const RhsValue &r) const -> word_t
The product (possibly concatenation) of l and r.
Definition: tupleset.hh:367
return res
Definition: multiply.hh:398
static size_t hash(const value_t &v)
Definition: tupleset.hh:506
tupleset_impl(ValueSets...ls)
Definition: tupleset.hh:113
std::tuple< typename ValueSets::value_t... > word_t
Same as value_t.
Definition: tupleset.hh:43
A traits so that tupleset may define types that may exist.
Definition: tupleset.hh:36
static constexpr bool is_labelset
Definition: tupleset.hh:44
ValueSet::value_t lgcd(const ValueSet &vs, const typename ValueSet::value_t &lhs, const typename ValueSet::value_t &rhs)
Left-division of values.
Definition: divide.hh:91
static auto letters_of(const Value &v) -> decltype(letters_of_(v, indices))
Iterate over the letters of v.
Definition: tupleset.hh:1130
value_t conv_(std::istream &i, bool quoted, std::false_type) const
Read a tuple in the stream, possibly parenthesized.
Definition: tupleset.hh:921
Print for LaTeX.
Definition: format.hh:22
bool is_special(const Aut &aut, transition_t_of< Aut > t)
Whether this transition is from pre or to post.
Definition: automaton.hh:228
static type join(const vs1_t &lhs, const vs2_t &rhs)
The resulting valueset.
Definition: tupleset.hh:1311
Functor to compare Values of ValueSets.
Definition: functional.hh:76
bool is_letter(const value_t &) const
Definition: tupleset.hh:344
value_t map_impl_(const value_t &l, const value_t &r, Fun &&fun, seq< I... >) const
Definition: tupleset.hh:859
value_t map_(const value_t &v, Fun &&fun) const
Apply a unary function pointwise, and return the tuple of results.
Definition: tupleset.hh:837
auto map_impl_(Fun f, const std::tuple< Ts... > &ts, index_sequence< I... >)
Definition: tuple.hh:185
Value delimit(const Value &l) const
Add the special character first and last.
Definition: tupleset.hh:478
Value delimit_(const Value &l, seq< I... >) const
Definition: tupleset.hh:886
Ignore its arguments.
Definition: raise.hh:18
static constexpr bool is_letterized_(seq< I... >)
Definition: tupleset.hh:1213
static bool is_one(const value_t &l)
Definition: tupleset.hh:332
std::ostream & print(const value_t &l, std::ostream &o=std::cout, format fmt={}) const
Definition: tupleset.hh:568
A traits to compute the letterized context.
Definition: labelset.hh:80
value_t conv_(std::istream &i, bool quoted, std::true_type) const
When the valuesets are labelsets and support one, accept the empty string to denote one...
Definition: tupleset.hh:910
value_t value(const std::tuple< Args... > &args) const
Construct a value.
Definition: tupleset.hh:202
always valid.
Definition: star-status.hh:17
An input/output format for valuesets.
Definition: format.hh:13
typename project_labelset_impl< Tape, LabelSet >::type project_labelset
The type of the resulting apparent LabelSet when keeping only tape Tape.
Definition: tupleset.hh:1341
weightset_mixin< detail::r_impl > r
Definition: fwd.hh:54
context join(const context &c1, const context &c2)
Bridge.
bool is_letterized(const Aut &aut)
Check if the transitions are all letters.
Definition: letterize.hh:190
value_t ldivide(const value_t &l, const value_t &r) const
Pointwise left division (l \ r).
Definition: tupleset.hh:419
static auto one() -> decltype(one_(Indices
A tuple of ones.
Definition: tupleset.hh:326
Provide a variadic mul on top of a binary mul(), and one().
Definition: fwd.hh:46
static labelset_t labelset(const tupleset< LabelSets... > &ls)
Definition: tupleset.hh:1222
The type of the resulting apparent LabelSet when keeping only tape Tape.
Definition: tupleset.hh:1336
static constexpr bool is_expressionset_(seq< I... >)
Definition: tupleset.hh:802
static bool show_one_(seq< I... >)
Definition: tupleset.hh:826
value_t zero_(seq< I... >) const
Definition: tupleset.hh:771
std::ostream & print_(const value_t &l, std::ostream &o, format fmt, const char *pre, const char *sep, const char *post, seq< I... >) const
Definition: tupleset.hh:964
valueset_t< 0 >::value_t lnormalize_here_(value_t &vs, seq< I... >) const
Definition: tupleset.hh:874
bool is_zero(const value_t &l) const
Definition: tupleset.hh:283
The smallest nullableset which includes LabelSet.
Definition: labelset.hh:139
boost::flyweight< std::string, boost::flyweights::no_tracking, boost::flyweights::intermodule_holder > symbol
An internalized string.
Definition: symbol.hh:23
static auto less_(const LhsValue &l, const RhsValue &r, seq< I... >) -> bool
Definition: tupleset.hh:728
static constexpr std::size_t size()
Number of tapes.
Definition: tupleset.hh:124
value_t conv(const tupleset< VS... > &vs, const typename tupleset< VS... >::value_t &v) const
Convert a value from tupleset<...> to value_t.
Definition: tupleset.hh:526
friend self_t meet(const self_t &lhs, const self_t &rhs)
The meet with another tupleset.
Definition: tupleset.hh:1041
genset_ptr genset_(seq< I... >) const
Definition: tupleset.hh:665
void convs(std::istream &i, Fun &&fun) const
Fun: (label_t) -> void.
Definition: tupleset.hh:552
static labelset_t labelset_(const tupleset< LabelSets... > &ls, seq< I... >)
Definition: tupleset.hh:1228
static void eat_separator_(std::istream &i)
Read the separator from the input stream i if I is not 0.
Definition: tupleset.hh:953
static bool is_special_(const value_t &l, seq< I... >)
Definition: tupleset.hh:761
tupleset< ValueSets... > make_tupleset(const ValueSets &...vss)
Definition: tupleset.hh:1152
static auto size_(const Value &v, int) -> decltype(valueset_t< I >::size(std::get< I >(v)))
The size of the Ith element, if its valueset features a size() function.
Definition: tupleset.hh:636
friend self_t meet(const self_t &lhs, const b &)
The meet with the B weightset.
Definition: tupleset.hh:1049
static constexpr bool is_free_(seq< I... >)
Definition: tupleset.hh:703
Definition: a-star.hh:8
static constexpr bool has_lightening_weights()
Definition: tupleset.hh:289
zip_sequences< Sequences... > zip(Sequences &&...seqs)
Definition: zip.hh:439
static constexpr bool is_letterized()
Definition: tupleset.hh:307
valuesets_t sets_
The tupled valuesets.
Definition: tupleset.hh:1063
static bool is_one_(const value_t &l, seq< I... >)
Definition: tupleset.hh:816
valueset_t< 0 >::value_t lnormalize_here(value_t &v) const
Eliminate the LGCD between all the tapes.
Definition: tupleset.hh:455
size_t size(const ExpSet &rs, const typename ExpSet::value_t &r)
bool is_zero_(const value_t &l, seq< I... >) const
Definition: tupleset.hh:778
typename labelset_types< ValueSets... >::letter_t letter_t
A tuple of base letters if meaningful, void otherwise.
Definition: tupleset.hh:91
Print as rich UTF-8 text, escaped.
Definition: format.hh:30
Value transpose_(const Value &l, seq< I... >) const
Definition: tupleset.hh:1025
static constexpr bool has_one_(seq< I... >)
Definition: tupleset.hh:795
A structure that implements the computation of join(V1, V2).
Definition: join.hh:18
static constexpr bool is_idempotent_(seq< I... >)
Definition: tupleset.hh:606
From a labelset, its non-nullable labelset.
Definition: labelset.hh:183
std::enable_if_t<!is_letterized_t< labelset_t_of< Aut > >{}, bool > is_letterized(const Aut &aut)
Definition: letterize.hh:161
The LAW from a LAL.
Definition: labelset.hh:250
static bool equal_(const value_t &l, const value_t &r, seq< I... >)
Definition: tupleset.hh:717
static constexpr star_status_t star_status()
Definition: tupleset.hh:492
auto make_gcc_tuple(Ts &&...ts) -> decltype(reverse_tuple(std::make_tuple(std::forward< Ts >(ts)...)))
Same as make_tuple, unless the evaluation of arguments if right-to-left, in which case reverse the re...
Definition: tuple.hh:342
Print as plain (ASCII) text, escaped.
Definition: format.hh:28
static value_t special_(seq< I... >)
Definition: tupleset.hh:754
Implementation of labels are nullables (letter or empty).
Definition: fwd.hh:14
tupleset_impl(valuesets_t vs)
Definition: tupleset.hh:109
auto word(const std::tuple< Args... > &v) const -> word_t
Convert to a word.
Definition: tupleset.hh:235
static auto one_(seq< I... >) -> decltype(value_t
Definition: tupleset.hh:314
static constexpr bool is_commutative()
Definition: tupleset.hh:137
void print_(std::ostream &o, const T &arg, long)
Serialize arg into o.
Definition: raise.hh:26
std::integral_constant< bool, B > bool_constant
Definition: type_traits.hh:12
value_t conv_(std::istream &i, bool quoted, seq< I... >) const
Definition: tupleset.hh:934
static constexpr bool is_free()
Definition: tupleset.hh:227
std::ostream & print_set(std::ostream &o, format fmt={}) const
Definition: tupleset.hh:562
auto tuple(const Auts &...as)
Build the (accessible part of the) tuple.
const valueset_t< I > & set() const
The Ith component valueset.
Definition: tupleset.hh:167
auto letters_of_padded(const Value &v, const std::tuple< Defaults... > &def) const -> decltype(this->letters_of_padded_(v, def, indices))
Iterate over the letters of v.
Definition: tupleset.hh:1143
genset_ptr genset() const
Definition: tupleset.hh:215
valueset_t< I > project_t
The type of the I-th tape valueset.
Definition: tupleset.hh:174
static constexpr bool has_one()
Definition: tupleset.hh:295
static value_t conv(self_t, value_t v)
Definition: tupleset.hh:512
tuple_element_t< I, valuesets_t > valueset_t
The Ith valueset type.
Definition: tupleset.hh:82
bool open(bool o) const
Whether unknown letters should be added, or rejected.
Definition: tupleset.hh:195
return v
Definition: multiply.hh:361
static std::string sname_(seq< I... >)
Definition: tupleset.hh:583
Provide a range that allows to iterate over the cross product of the provided ranges.
Definition: cross.hh:16
boost::optional< value_t > maybe_rdivide(const value_t &l, const value_t &r) const
Definition: tupleset.hh:396
star_status_t
Definition: star-status.hh:5
static size_t size_(const Value &v, seq< I... >)
Definition: tupleset.hh:652
symbol sname()
Definition: name.hh:65
value_t conv(std::istream &i, bool quoted=true) const
Read one label from i, return the corresponding value.
Definition: tupleset.hh:543
const valuesets_t & sets() const
The componants valuesets, as a tuple.
Definition: tupleset.hh:160
typename std::tuple_element< I, T >::type tuple_element_t
C++14.
Definition: tuple.hh:14
value_t tuple(Args &&...args) const
Construct a value.
Definition: tupleset.hh:209
value_t lgcd(const value_t &l, const value_t &r) const
Pointwise left GCD.
Definition: tupleset.hh:375
static constexpr auto size_(const Value &,...) -> size_t
The size of the Ith element, if its valueset does not feature a size() function.
Definition: tupleset.hh:645
typename detail::weightset_t_of_impl< base_t< ValueSet >>::type weightset_t_of
Definition: traits.hh:67
tupleset< LabelSet... >::value_t random_label_(const tupleset< LabelSet... > &ls, RandomGenerator &gen, detail::index_sequence< I... >)
Implementation detail for random label from tupleset.
Definition: tupleset.hh:1393
weightset_mixin< detail::tupleset_impl< LabelSets... >> tupleset
Definition: fwd.hh:27
static self_t make_(std::istream &i, seq< I... >)
Definition: tupleset.hh:612
static auto letters_of_(const Value &v, seq< I... >) -> decltype(zip(valueset_t< I >::letters_of(std::get< I >(v))...))
Must be declared before, as we use its result in decltype.
Definition: tupleset.hh:1088
auto conv(const ValueSet &vs, const std::string &str, Args &&...args) -> decltype(vs.conv(std::declval< std::istream & >(), std::forward< Args >(args)...))
Parse str via vs.conv.
Definition: stream.hh:29
typename valueset_t::template project_t< Tape > type
Definition: tupleset.hh:1356
static size_t size(const Value &v)
Get the max of the sizes of the tapes.
Definition: tupleset.hh:131
cross_sequences< Sequences... > cross(Sequences &&...seqs)
Definition: cross.hh:287
auto join(const ValueSet &vs) -> ValueSet
The join of a single valueset.
Definition: join.hh:44
static type value(const labelset_t &ls)
Definition: tupleset.hh:1286
static symbol sname()
Definition: tupleset.hh:117
value_t zero() const
Definition: tupleset.hh:277
Value undelimit_(const Value &l, seq< I... >) const
Definition: tupleset.hh:893
LabelSet::letters_t conv_label_class_(const LabelSet &ls, std::istream &i)
Read a set of letters (hence, guaranteed in order, and unique).
Definition: labelset.hh:442
static auto less(const LhsValue &l, const RhsValue &r) -> bool
Whether l < r.
Definition: tupleset.hh:251
auto get_letter_(std::istream &i, bool quoted, seq< I... >) const -> letter_t
Must be declared before, as we use its result in decltype.
Definition: tupleset.hh:1071
auto get_letter(std::istream &i, bool quoted=true) const -> decltype(this->get_letter_(i, quoted, indices))
Definition: tupleset.hh:1111
std::tuple< typename ValueSets::value_t... > value_t
A tuple of values.
Definition: tupleset.hh:88
expressionset< Context >::value_t random_label(const expressionset< Context > &rs, RandomGenerator &gen=RandomGenerator())
Random label from expressionset: limited to a single label.
value_t map_impl_(const value_t &v, Fun &&fun, seq< I... >) const
Definition: tupleset.hh:844
typename valueset_t::template project_t< Tape > type
Definition: tupleset.hh:1348
auto letters_of_padded_(const Value &v, const std::tuple< Defaults... > &def, seq< I... >) const -> decltype(zip_with_padding(def, this->set< I >().letters_of_padded(std::get< I >(v), std::get< I >(def))...))
Must be declared before, as we use its result in decltype.
Definition: tupleset.hh:1097
value_t rdivide(const value_t &l, const value_t &r) const
Pointwise right division (l / r).
Definition: tupleset.hh:386
void hash_combine(std::size_t &seed, const T &v)
Definition: functional.hh:48
const valueset_t< I > & project() const
The Ith component valueset.
Definition: tupleset.hh:180
zip_sequences_padded< zip_sequences< Sequences... > > zip_with_padding(const std::tuple< typename Sequences::value_type... > &pad, const Sequences &...seq)
Definition: zip.hh:453
value_t map_(const value_t &l, const value_t &r, Fun &&fun) const
Apply a binary function pointwise, and return the tuple of results.
Definition: tupleset.hh:852
auto generators() const
The generators. Meaningful for labelsets only.
Definition: tupleset.hh:222
Value transpose(const Value &l) const
Transpose a word_t or a value_t.
Definition: tupleset.hh:500
boost::optional< value_t > maybe_ldivide(const value_t &l, const value_t &r) const
Definition: tupleset.hh:429
static constexpr bool is_letterized_(seq< I... >)
Definition: tupleset.hh:809
auto project(const value_t &v) const
The I-th component of the value.
Definition: tupleset.hh:187
Value undelimit(const Value &l) const
Remove first and last characters, that must be "special".
Definition: tupleset.hh:486
format_t kind() const
Definition: format.hh:98
typename labelset_types< ValueSets... >::letters_t letters_t
A set of letters if meaningful, void otherwise.
Definition: tupleset.hh:93
value_t star(const value_t &v) const
Pointwise star.
Definition: tupleset.hh:462
static std::size_t hash_(const value_t &v, seq< I... >)
Definition: tupleset.hh:744
typename labelset_types< ValueSets... >::genset_ptr genset_ptr
A tuple of generators if meaningful, void otherwise.
Definition: tupleset.hh:96
static self_t make(std::istream &is)
Build from the description in is.
Definition: tupleset.hh:149
auto meet(const expressionset< Ctx1 > &a, const expressionset< Ctx2 > &b) -> expressionset< meet_t< Ctx1, Ctx2 >>
The meet of two expressionsets.
std::ostream & print_set_(std::ostream &o, format fmt, seq< I... >) const
Definition: tupleset.hh:987
letterized_t< LabelSet > make_letterized(const LabelSet &ls)
Definition: labelset.hh:101
bool open_(bool o, seq< I... >) const
Definition: tupleset.hh:625
A ValueSet which is a Cartesian product of ValueSets.
Definition: fwd.hh:23
Whether a ValueSet, or a context, is multitape.
Definition: tupleset.hh:1164
static type value(const labelset_t &ls, index_sequence< I... >)
Definition: tupleset.hh:1281
self_t meet_(const self_t &rhs, seq< I... >) const
The intersection with another tupleset.
Definition: tupleset.hh:1033
word_t word_(const std::tuple< Args... > &l, seq< I... >) const
Definition: tupleset.hh:710
static constexpr bool is_idempotent()
Definition: tupleset.hh:143
Request the set implementation (bool weights).
law_t< LabelSet > make_wordset(const LabelSet &ls)
The wordset of a labelset.
Definition: labelset.hh:260
static type value(const tupleset< LabelSet > &ls)
Definition: tupleset.hh:1267
Aut transpose(const transpose_automaton< Aut > &aut)
The transpose of a transpose automaton is the original automaton.
Definition: transpose.hh:253
static type join(const vs1_t &lhs, const vs2_t &rhs, index_sequence< I... >)
Definition: tupleset.hh:1304
filter_automaton< Aut, Trans > filter(const Aut &aut, boost::optional< dynamic_bitset > ss={}, boost::optional< dynamic_bitset > ts={})
Get an automaton who is a part state set ss of aut.
Definition: filter.hh:301
value_t conv_(const tupleset< VS... > &vs, const typename tupleset< VS... >::value_t &v, seq< I... >) const
Definition: tupleset.hh:900
auto mul_(const LhsValue &l, const RhsValue &r, seq< I... >) const -> word_t
Definition: tupleset.hh:866