libsemigroups  v3.0.0
C++ library for semigroups and monoids
Loading...
Searching...
No Matches
presentation.hpp
1//
2// libsemigroups - C++ library for semigroups and monoids
3// Copyright (C) 2022-2025 James D. Mitchell
4//
5// This program is free software: you can redistribute it and/or modify
6// it under the terms of the GNU General Public License as published by
7// the Free Software Foundation, either version 3 of the License, or
8// (at your option) any later version.
9//
10// This program is distributed in the hope that it will be useful,
11// but WITHOUT ANY WARRANTY; without even the implied warranty of
12// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13// GNU General Public License for more details.
14//
15// You should have received a copy of the GNU General Public License
16// along with this program. If not, see <http://www.gnu.org/licenses/>.
17//
18
19// This file contains the declaration of a class template for semigroup or
20// monoid presentations. The idea is to provide a shallow wrapper around a
21// vector of words, with some checks that the vector really defines a
22// presentation, (i.e. it's consistent with its alphabet etc), and some related
23// functionality.
24
25#ifndef LIBSEMIGROUPS_PRESENTATION_HPP_
26#define LIBSEMIGROUPS_PRESENTATION_HPP_
27
28#include <algorithm> // for reverse, sort
29#include <cctype> // for isprint
30#include <cmath> // for pow
31#include <cstring> // for size_t, strlen
32#include <initializer_list> // for initializer_list
33#include <iterator> // for distance
34#include <limits> // for numeric_limits
35#include <map> // for map
36#include <numeric> // for accumulate
37#include <string> // for basic_string, operator==
38#include <tuple> // for tie, tuple
39#include <type_traits> // for enable_if_t
40#include <unordered_map> // for operator==, operator!=
41#include <unordered_set> // for unordered_set
42#include <utility> // for move, pair
43#include <vector> // for vector, operator!=
44
45#include "adapters.hpp" // for Hash, EqualTo
46#include "constants.hpp" // for Max, UNDEFINED, operator==
47#include "debug.hpp" // for LIBSEMIGROUPS_ASSERT
48#include "order.hpp" // for ShortLexCompare
49#include "ranges.hpp" // for seq, operator|, rx, take, chain, is_sorted
50#include "types.hpp" // for word_type
51#include "ukkonen.hpp" // for GreedyReduceHelper, Ukkonen
52#include "word-range.hpp" // for operator+
53
54#include "detail/fmt.hpp" // for format
55#include "detail/string.hpp" // for maximum_common_prefix
56#include "detail/uf.hpp" // for Duf
57
58namespace libsemigroups {
59
75
78
101 template <typename Word>
103 public:
105 using word_type = Word;
106
109 using letter_type = typename word_type::value_type;
110
113
116
119
120 private:
121 word_type _alphabet;
123 bool _contains_empty_word;
124
125 public:
132
137
149
154
159
164
169
171
183 [[nodiscard]] word_type const& alphabet() const noexcept {
184 return _alphabet;
185 }
186
187 // TODO(later) alphabet_no_checks
188
209 // TODO(1) Rename alphabet_size
211
231
251
269
283 [[nodiscard]] letter_type letter_no_checks(size_type i) const {
284 LIBSEMIGROUPS_ASSERT(i < _alphabet.size());
285 return _alphabet[i];
286 }
287
298 [[nodiscard]] letter_type letter(size_type i) const;
299
316 [[nodiscard]] size_type index_no_checks(letter_type val) const {
317 return _alphabet_map.find(val)->second;
318 }
319
330 [[nodiscard]] size_type index(letter_type val) const;
331
345 [[nodiscard]] bool in_alphabet(letter_type val) const {
346 return _alphabet_map.find(val) != _alphabet_map.cend();
347 }
348
384 template <typename Iterator1, typename Iterator2>
385 Presentation& add_rule_no_checks(Iterator1 lhs_begin,
386 Iterator1 lhs_end,
387 Iterator2 rhs_begin,
388 Iterator2 rhs_end) {
389 rules.emplace_back(lhs_begin, lhs_end);
390 rules.emplace_back(rhs_begin, rhs_end);
391 return *this;
392 }
393
408 template <typename Iterator1, typename Iterator2>
409 Presentation& add_rule(Iterator1 lhs_begin,
410 Iterator1 lhs_end,
411 Iterator2 rhs_begin,
412 Iterator2 rhs_end) {
413 throw_if_letter_not_in_alphabet(lhs_begin, lhs_end);
414 throw_if_letter_not_in_alphabet(rhs_begin, rhs_end);
415 return add_rule_no_checks(lhs_begin, lhs_end, rhs_begin, rhs_end);
416 }
417
428
438
447
466
479
496 [[nodiscard]] bool contains_empty_word() const noexcept {
497 return _contains_empty_word;
498 }
499
519 Presentation& contains_empty_word(bool val) noexcept {
520 _contains_empty_word = val;
521 return *this;
522 }
523
534 decltype(_alphabet_map) alphabet_map;
536 }
537
549
564 template <typename Iterator1, typename Iterator2>
565 void throw_if_letter_not_in_alphabet(Iterator1 first, Iterator2 last) const;
566
583 void throw_if_bad_rules() const;
584
600
601 private:
602 void try_set_alphabet(decltype(_alphabet_map)& alphabet_map,
603 word_type& old_alphabet);
605 decltype(_alphabet_map)& alphabet_map) const;
606 }; // class Presentation
607
616 template <typename Word>
618
627 template <typename Word>
629
640 namespace presentation {
641
654 template <typename Iterator>
655 void throw_if_odd_number_of_rules(Iterator first, Iterator last) {
656 if ((std::distance(first, last) % 2) == 1) {
658 "expected even number of words in \"rules\", found {}",
659 std::distance(first, last));
660 }
661 }
662
674 template <typename Word>
678
695 template <typename Word>
697 std::string_view arg = "1st") {
698 auto first = std::begin(p.alphabet()), last = std::end(p.alphabet());
699 if (!std::is_sorted(first, last)) {
700 LIBSEMIGROUPS_EXCEPTION("the {} argument (presentation) must have "
701 "sorted alphabet, found {}",
702 arg,
703 p.alphabet());
704 }
705
706 auto it = std::max_element(first, last);
707 if (it != last && *it != p.alphabet().size() - 1) {
708 LIBSEMIGROUPS_EXCEPTION("the {} argument (presentation) has invalid "
709 "alphabet, expected [0, ..., {}] found {}",
710 arg,
711 p.alphabet().size() - 1,
712 p.alphabet());
713 }
714 }
715
734 template <typename Word, typename Iterator>
736 Iterator first,
737 Iterator last) {
738 // TODO(0) check if there are an odd number of rules
739 for (auto it = first; it != last; ++it) {
740 p.throw_if_letter_not_in_alphabet(it->cbegin(), it->cend());
741 }
742 }
743
766 template <typename Word>
767 void throw_if_bad_inverses(Presentation<Word> const& p, Word const& vals);
768
785 template <typename Word>
787 Word const& lhop,
788 Word const& rhop) {
789 p.add_rule_no_checks(lhop.begin(), lhop.end(), rhop.begin(), rhop.end());
790 }
791
805 template <typename Word>
806 void add_rule(Presentation<Word>& p, Word const& lhop, Word const& rhop) {
807 p.add_rule(lhop.begin(), lhop.end(), rhop.begin(), rhop.end());
808 }
809
826 char const* lhop,
827 char const* rhop);
828
841 char const* lhop,
842 char const* rhop);
843
857 std::string const& lhop,
858 char const* rhop);
859
873 char const* lhop,
874 std::string const& rhop);
875
893 std::string const& lhop,
894 char const* rhop);
895
913 char const* lhop,
914 std::string const& rhop);
915
933 template <typename Word, typename Letter>
939
953 template <typename Word, typename Letter>
957 p.add_rule(lhop.begin(), lhop.end(), rhop.begin(), rhop.end());
958 }
959
978 template <typename Word, typename Iterator>
979 void add_rules(Presentation<Word>& p, Iterator first, Iterator last) {
980 for (auto it = first; it != last; it += 2) {
981 add_rule(p, *it, *(it + 1));
982 }
983 }
984
1002 template <typename Word, typename Iterator>
1004 Iterator first,
1005 Iterator last) {
1006 for (auto it = first; it != last; it += 2) {
1007 add_rule_no_checks(p, *it, *(it + 1));
1008 }
1009 }
1010
1026 template <typename Word>
1031
1048 template <typename Word>
1050 add_rules(p, q.rules.cbegin(), q.rules.cend());
1051 }
1052
1070 template <typename Word>
1071 [[nodiscard]] bool contains_rule(Presentation<Word>& p,
1072 Word const& lhs,
1073 Word const& rhs);
1074
1089 template <typename Word>
1092
1107 template <typename Word>
1110
1134 template <typename Word>
1136 Word const& vals,
1138 = UNDEFINED);
1139
1164 char const* vals,
1165 char e = UNDEFINED);
1166
1181 template <typename Word>
1183
1196 template <typename Word>
1198
1219 template <typename Word>
1221
1234 template <typename Word>
1236
1252 template <typename Word, typename Compare>
1253 bool sort_each_rule(Presentation<Word>& p, Compare cmp);
1254
1255 // TODO(later) is_each_rule_sorted?
1256
1269 template <typename Word, typename Compare>
1270 void sort_rules(Presentation<Word>& p, Compare cmp);
1271
1281 template <typename Word>
1285
1303 template <typename Word, typename Compare>
1304 bool are_rules_sorted(Presentation<Word> const& p, Compare cmp);
1305
1320 template <typename Word>
1322 return are_rules_sorted(p, ShortLexCompare());
1323 }
1324
1341 // TODO(later) complexity
1342 template <typename Word>
1344
1359 // TODO(later) complexity
1360 template <typename Word, typename Iterator>
1363 Iterator first,
1364 Iterator last);
1365
1382 // TODO(later) complexity
1383 template <typename Word>
1386 return replace_word_with_new_generator(p, w.cbegin(), w.cend());
1387 }
1388
1405 char const* w);
1406
1419 // TODO(later) complexity
1420 template <typename Word>
1422 Word const& existing,
1423 Word const& replacement);
1424
1448 template <typename Word, typename Iterator1, typename Iterator2>
1450 Iterator1 first_existing,
1451 Iterator1 last_existing,
1452 Iterator2 first_replacement,
1453 Iterator2 last_replacement);
1454
1468 char const* existing,
1469 char const* replacement) {
1471 existing,
1472 existing + std::strlen(existing),
1473 replacement,
1474 replacement + std::strlen(replacement));
1475 }
1476
1493 template <typename Word>
1495 Word const& existing,
1496 Word const& replacement);
1497
1514 template <typename Iterator>
1515 size_t length(Iterator first, Iterator last);
1516
1528 template <typename Word>
1529 size_t length(Presentation<Word> const& p) {
1530 return length(p.rules.cbegin(), p.rules.cend());
1531 }
1532
1542 template <typename Word>
1544 for (auto& rule : p.rules) {
1545 std::reverse(rule.begin(), rule.end());
1546 }
1547 }
1548
1560 // This is the only place that JDE can find where a helper that modifies its
1561 // first argument is not void. This is deliberate, since if we weren't to
1562 // return anything, the first parameter would go out of scope immediately
1563 // after this call and this function would be pointless .
1564 template <typename Word>
1566 for (auto& rule : p.rules) {
1567 std::reverse(rule.begin(), rule.end());
1568 }
1569 return std::move(p);
1570 }
1571
1586 template <typename Word>
1588
1602 template <typename Word>
1603 void change_alphabet(Presentation<Word>& p, Word const& new_alphabet);
1604
1617 char const* new_alphabet) {
1618 change_alphabet(p, std::string(new_alphabet));
1619 }
1620
1638 template <typename Iterator>
1639 Iterator longest_rule(Iterator first, Iterator last);
1640
1656 template <typename Word>
1659 return longest_rule(p.rules.cbegin(), p.rules.cend());
1660 }
1661
1679 template <typename Iterator>
1680 Iterator shortest_rule(Iterator first, Iterator last);
1681
1697 template <typename Word>
1700 return shortest_rule(p.rules.cbegin(), p.rules.cend());
1701 }
1702
1717 template <typename Iterator>
1718 typename Iterator::value_type::size_type longest_rule_length(Iterator first,
1719 Iterator last);
1720
1734 template <typename Word>
1735 typename Word::size_type longest_rule_length(Presentation<Word> const& p) {
1736 return longest_rule_length(p.rules.cbegin(), p.rules.cend());
1737 }
1738
1753 template <typename Iterator>
1754 typename Iterator::value_type::size_type
1755 shortest_rule_length(Iterator first, Iterator last);
1756
1770 template <typename Word>
1771 typename Word::size_type shortest_rule_length(Presentation<Word> const& p) {
1772 return shortest_rule_length(p.rules.cbegin(), p.rules.cend());
1773 }
1774
1789 template <typename Word>
1791
1807 template <typename Word>
1810
1827 template <typename Word>
1830
1847 template <typename Word>
1849
1872 template <typename Word>
1874
1897 // not noexcept because std::vector::operator[] isn't
1898 template <typename Word>
1900
1920 // not noexcept because is_strongly_compressible isn't
1921 template <typename Word>
1923
1952 template <typename Word>
1953 bool reduce_to_2_generators(Presentation<Word>& p, size_t index = 0);
1954
1970 template <typename Word>
1972 Word const& letters) {
1973 for (auto x : letters) {
1974 add_rule_no_checks(p, {x, x}, {x});
1975 }
1976 }
1977
1993 template <typename Word>
1995 word_type const& letters) {
1996 for (auto x : letters) {
1997 add_rule_no_checks(p, {x, x}, {});
1998 }
1999 }
2000
2017 template <typename Word>
2019 Word const& letters1,
2020 Word const& letters2);
2021
2037 template <typename Word>
2039 Word const& letters) {
2040 add_commutes_rules_no_checks(p, letters, letters);
2041 }
2042
2059 template <typename Word>
2061 Word const& letters,
2063
2091 template <typename Word1, typename Word2>
2093 Word2 const& letters,
2094 Word2 const& inverses);
2095
2102 template <typename Word>
2104 Word const& letters,
2105 Word const& inverses) {
2106 balance_no_checks<Word, Word>(p, letters, inverses);
2107 }
2108
2116 char const* letters,
2117 char const* inverses) {
2119 p, std::string_view(letters), std::string_view(inverses));
2120 }
2121
2129 std::string_view letters,
2130 std::string_view inverses) {
2132 }
2133
2134 // TODO(later) add balance that checks p contains empty word, no duplicate
2135 // letters in alphabet, and inverses are valid.
2136
2137 // // TODO(later) do a proper version of this, where the inverses are
2138 // // specified, rather than being assumed to be upper/lower cases
2139 // template <typename Word>
2140 // void add_cyclic_conjugates(Presentation<Word>& p,
2141 // Word const& lhs,
2142 // Word const& rhs);
2143
2156 std::string const& var_name);
2157
2170 std::string const& var_name);
2171
2172 } // namespace presentation
2173
2187 template <typename Word>
2188 class InversePresentation : public Presentation<Word> {
2189 public:
2193
2197
2200
2203
2206
2207 private:
2208 word_type _inverses;
2209
2210 public:
2211 using Presentation<Word>::Presentation;
2212
2213 // TODO(later) init functions
2214
2223 : Presentation<Word>(p), _inverses() {}
2224
2234 : Presentation<Word>(p), _inverses() {}
2235
2252
2279
2288 word_type const& inverses() const noexcept {
2289 return _inverses;
2290 }
2291
2303
2320 // TODO(0) check if this is used appropriately after rename
2323 }
2324 };
2325
2344 // TODO(later) also we could do a more sophisticated version of this
2345 template <typename Word>
2347 Presentation<Word> const& rhop) {
2348 return lhop.alphabet() == rhop.alphabet() && lhop.rules == rhop.rules;
2349 }
2350
2369 // TODO(later) also we could do a more sophisticated version of this
2370 template <typename Word>
2372 InversePresentation<Word> const& rhop) {
2373 return lhop.alphabet() == rhop.alphabet() && lhop.rules == rhop.rules
2374 && lhop.inverses() == rhop.inverses();
2375 }
2376
2395 template <typename Word>
2397 Presentation<Word> const& rhop) {
2398 return !(lhop == rhop);
2399 }
2400
2419 template <typename Word>
2421 InversePresentation<Word> const& rhop) {
2422 return !(lhop == rhop);
2423 }
2424
2436 template <typename Word>
2438
2450 template <typename Word>
2452
2453 namespace detail {
2454 template <typename T>
2455 struct IsPresentationHelper : std::false_type {};
2456
2457 template <typename T>
2458 struct IsPresentationHelper<Presentation<T>> : std::true_type {};
2459
2460 template <typename T>
2461 struct IsPresentationHelper<InversePresentation<T>> : std::true_type {};
2462
2463 template <typename T>
2464 struct IsInversePresentationHelper : std::false_type {};
2465
2466 template <typename T>
2467 struct IsInversePresentationHelper<InversePresentation<T>>
2468 : std::true_type {};
2469
2470 class GreedyReduceHelper {
2471 private:
2472 size_t _best;
2473 int _best_goodness;
2474 std::vector<size_t> _distance_from_root;
2475 std::vector<size_t> _num_leafs;
2476 std::vector<size_t> _scratch;
2477 std::vector<size_t> _suffix_index;
2478
2479 public:
2480 using const_iterator = typename Ukkonen::const_iterator;
2481
2482 explicit GreedyReduceHelper(Ukkonen const& u);
2483
2484 GreedyReduceHelper() = delete;
2485 GreedyReduceHelper(GreedyReduceHelper const&) = delete;
2486 GreedyReduceHelper(GreedyReduceHelper&&) = delete;
2487 GreedyReduceHelper& operator=(GreedyReduceHelper const&) = delete;
2488 GreedyReduceHelper& operator=(GreedyReduceHelper&&) = delete;
2489 ~GreedyReduceHelper();
2490
2491 void pre_order(Ukkonen const& u, size_t v);
2492 void post_order(Ukkonen const& u, size_t v);
2493 std::pair<const_iterator, const_iterator> yield(Ukkonen const& u);
2494 };
2495 } // namespace detail
2496
2507 template <typename T>
2508 static constexpr bool IsInversePresentation
2509 = detail::IsInversePresentationHelper<T>::value;
2510
2521 template <typename T>
2522 static constexpr bool IsPresentation = detail::IsPresentationHelper<T>::value;
2523
2524} // namespace libsemigroups
2525
2526#include "presentation.tpp"
2527
2528#endif // LIBSEMIGROUPS_PRESENTATION_HPP_
T cbegin(T... args)
For an implementation of inverse presentations for semigroups or monoids.
Definition presentation.hpp:2188
typename Presentation< Word >::size_type size_type
Size type for rules.
Definition presentation.hpp:2205
typename Presentation< Word >::letter_type letter_type
Type of the letters in the words that constitute the rules of an InversePresentation object.
Definition presentation.hpp:2196
void throw_if_bad_alphabet_rules_or_inverses() const
Check if the InversePresentation is valid.
Definition presentation.hpp:2319
typename Presentation< Word >::iterator iterator
Type of an iterator to either side of a rule.
Definition presentation.hpp:2202
InversePresentation(Presentation< Word > const &p)
Construct an InversePresentation from a Presentation reference.
Definition presentation.hpp:2222
typename Presentation< Word >::word_type word_type
Type of the words in the rules of an InversePresentation object.
Definition presentation.hpp:2192
letter_type inverse(letter_type x) const
Return the inverse of a letter in the alphabet.
InversePresentation & inverses(word_type const &w)
Set the inverse of each letter in the alphabet.
Definition presentation.hpp:2274
InversePresentation(Presentation< Word > &&p)
Construct an InversePresentation from a Presentation rvalue reference.
Definition presentation.hpp:2233
word_type const & inverses() const noexcept
Return the inverse of each letter in the alphabet.
Definition presentation.hpp:2288
InversePresentation & inverses_no_checks(word_type const &w)
Set the inverse of each letter in the alphabet.
typename Presentation< Word >::const_iterator const_iterator
Type of a const iterator to either side of a rule.
Definition presentation.hpp:2199
For an implementation of presentations for semigroups or monoids.
Definition presentation.hpp:102
letter_type add_generator()
Add a generator.
void remove_generator(letter_type x)
Remove x as a generator.
Presentation & alphabet(word_type &&lphbt)
Set the alphabet from rvalue reference.
void throw_if_bad_alphabet_or_rules() const
Check if the alphabet and rules are valid.
Definition presentation.hpp:596
void throw_if_bad_rules() const
Check if every word in every rule consists only of letters belonging to the alphabet.
Presentation & contains_empty_word(bool val) noexcept
Set whether whether the empty word is a valid relation word.
Definition presentation.hpp:519
typename std::vector< word_type >::size_type size_type
Size type for rules.
Definition presentation.hpp:118
void add_generator(letter_type x)
Add x as a generator.
void throw_if_letter_not_in_alphabet(letter_type c) const
Check if a letter belongs to the alphabet or not.
size_type index_no_checks(letter_type val) const
Return the index of a letter in the alphabet.
Definition presentation.hpp:316
Presentation & alphabet(size_type n)
Set the alphabet by size.
Presentation & alphabet_from_rules()
Set the alphabet to be the letters in the rules.
Presentation & operator=(Presentation &&)
Default move assignment operator.
Presentation & add_rule_no_checks(Iterator1 lhs_begin, Iterator1 lhs_end, Iterator2 rhs_begin, Iterator2 rhs_end)
Add a rule to the presentation.
Definition presentation.hpp:385
typename std::vector< word_type >::iterator iterator
Type of an iterator to either side of a rule.
Definition presentation.hpp:115
Presentation(Presentation const &)
Default copy constructor.
void throw_if_alphabet_has_duplicates() const
Check if the alphabet is valid.
Definition presentation.hpp:533
letter_type letter_no_checks(size_type i) const
Return a letter in the alphabet by index.
Definition presentation.hpp:283
void throw_if_letter_not_in_alphabet(Iterator1 first, Iterator2 last) const
Check if every letter in a range belongs to the alphabet.
Presentation(Presentation &&)
Default move constructor.
letter_type letter(size_type i) const
Return a letter in the alphabet by index.
std::vector< word_type > rules
Data member holding the rules of the presentation.
Definition presentation.hpp:131
Presentation & operator=(Presentation const &)
Default copy assignment operator.
bool contains_empty_word() const noexcept
Return whether the empty word is a valid relation word.
Definition presentation.hpp:496
Presentation & alphabet(word_type const &lphbt)
Set the alphabet const reference.
size_type index(letter_type val) const
Return the index of a letter in the alphabet.
Presentation & init()
Remove the alphabet and all rules.
word_type const & alphabet() const noexcept
Return the alphabet of the presentation.
Definition presentation.hpp:183
Word word_type
Type of the words in the rules of a Presentation object.
Definition presentation.hpp:105
typename word_type::value_type letter_type
Type of the letters in the words that constitute the rules of a Presentation object.
Definition presentation.hpp:109
void add_generator_no_checks(letter_type x)
Add x as a generator.
void remove_generator_no_checks(letter_type x)
Remove x as a generator.
Presentation()
Default constructor.
typename std::vector< word_type >::const_iterator const_iterator
Type of a const iterator to either side of a rule.
Definition presentation.hpp:112
Presentation & add_rule(Iterator1 lhs_begin, Iterator1 lhs_end, Iterator2 rhs_begin, Iterator2 rhs_end)
Add a rule to the presentation and check it is valid.
Definition presentation.hpp:409
bool in_alphabet(letter_type val) const
Check if a letter belongs to the alphabet or not.
Definition presentation.hpp:345
typename word_type::const_iterator const_iterator
Alias for word_type iterators.
Definition ukkonen.hpp:97
T distance(T... args)
T cend(T... args)
std::string to_human_readable_repr(AhoCorasick const &ac)
Return a string representation.
bool operator!=(Bipartition const &x, Bipartition const &y)
Check bipartitions for inequality.
Definition bipart.hpp:1637
Undefined const UNDEFINED
Value for something undefined.
#define LIBSEMIGROUPS_EXCEPTION(...)
Throw a LibsemigroupsException.
Definition exception.hpp:95
Presentation(Presentation< Word > const &) -> Presentation< Word >
Deduction guide.
bool operator==(Presentation< Word > const &lhop, Presentation< Word > const &rhop)
Compare for equality.
Definition presentation.hpp:2346
static constexpr bool IsPresentation
Helper variable template.
Definition presentation.hpp:2522
static constexpr bool IsInversePresentation
Helper variable template.
Definition presentation.hpp:2509
std::vector< letter_type > word_type
Type for a word over the generators of a semigroup.
Definition types.hpp:101
T is_sorted(T... args)
T max_element(T... args)
T move(T... args)
Namespace for Presentation helper functions.
Definition obvinf.hpp:59
Iterator::value_type::size_type longest_rule_length(Iterator first, Iterator last)
Return the maximum length of a rule in the given range.
void add_commutes_rules_no_checks(Presentation< Word > &p, Word const &letters1, Word const &letters2)
Add rules so specific letters commute.
Presentation< Word >::letter_type replace_word_with_new_generator(Presentation< Word > &p, Iterator first, Iterator last)
Replace non-overlapping instances of a subword via iterators.
bool reduce_to_2_generators(Presentation< Word > &p, size_t index=0)
Reduce the number of generators in a -relation presentation to 2.
void add_idempotent_rules_no_checks(Presentation< Word > &p, Word const &letters)
Add rules that define each letter as an idempotent.
Definition presentation.hpp:1971
void throw_if_bad_inverses(Presentation< Word > const &p, Word const &vals)
throw_if_bad_alphabet_or_rules if vals act as semigroup inverses in p.
Iterator longest_rule(Iterator first, Iterator last)
Return an iterator pointing at the left-hand side of the first rule of maximal length in the given ra...
void add_involution_rules_no_checks(Presentation< Word > &p, word_type const &letters)
Add rules that define involution.
Definition presentation.hpp:1994
void throw_if_odd_number_of_rules(Iterator first, Iterator last)
Throw if the distance between iterators is not even.
Definition presentation.hpp:655
void reverse(Presentation< Word > &p)
Reverse every rule.
Definition presentation.hpp:1543
bool contains_rule(Presentation< Word > &p, Word const &lhs, Word const &rhs)
Check if a presentation contains a rule.
void greedy_reduce_length_and_number_of_gens(Presentation< Word > &p)
Greedily reduce the length and number of generators of the presentation.
Word longest_subword_reducing_length(Presentation< Word > &p)
Return the longest common subword of the rules.
bool sort_each_rule(Presentation< Word > &p)
Sort the left-hand and right-hand side of each rule by shortlex.
bool are_rules_sorted(Presentation< Word > const &p, Compare cmp)
Check the rules are sorted relative to cmp .
void add_rules(Presentation< Word > &p, Iterator first, Iterator last)
Add the rules stored in the range [first, last).
Definition presentation.hpp:979
Iterator shortest_rule(Iterator first, Iterator last)
Return an iterator pointing at the left-hand side of the first rule of minimal length in the given ra...
void balance_no_checks(Presentation< Word1 > &p, Word2 const &letters, Word2 const &inverses)
Balance the length of the left-hand and right-hand sides.
Iterator::value_type::size_type shortest_rule_length(Iterator first, Iterator last)
Return the minimum length of a rule in the given range.
void remove_trivial_rules(Presentation< Word > &p)
Remove rules consisting of identical words.
void add_rules_no_checks(Presentation< Word > &p, Iterator first, Iterator last)
Add the rules stored in the range [first, last).
Definition presentation.hpp:1003
void replace_word(Presentation< Word > &p, Word const &existing, Word const &replacement)
Replace instances of a word on either side of a rule by another word.
void add_rule_no_checks(Presentation< Word > &p, Word const &lhop, Word const &rhop)
Add a rule to the presentation by reference.
Definition presentation.hpp:786
void throw_if_bad_rules(Presentation< Word > const &p, Iterator first, Iterator last)
Check rules against the alphabet of p.
Definition presentation.hpp:735
void sort_rules(Presentation< Word > &p, Compare cmp)
Sort all of the rules by cmp.
void replace_subword(Presentation< Word > &p, Word const &existing, Word const &replacement)
Replace non-overlapping instances of a subword by another word.
void add_identity_rules(Presentation< Word > &p, typename Presentation< Word >::letter_type e)
Add rules for an identity element.
Presentation< Word >::letter_type make_semigroup(Presentation< Word > &p)
Convert a monoid presentation to a semigroup presentation.
void reduce_complements(Presentation< Word > &p)
If there are rules and where , then replace by .
void normalize_alphabet(Presentation< Word > &p)
Normalize the alphabet to .
bool strongly_compress(Presentation< Word > &p)
Strongly compress a -relation presentation.
void remove_redundant_generators(Presentation< Word > &p)
Remove any trivially redundant generators.
void greedy_reduce_length(Presentation< Word > &p)
Greedily reduce the length of the presentation using longest_subword_reducing_length.
void change_alphabet(Presentation< Word > &, Word const &)
Change or re-order the alphabet.
void add_inverse_rules(Presentation< Word > &p, Word const &vals, typename Presentation< Word >::letter_type e=UNDEFINED)
Add rules for inverses.
bool is_strongly_compressible(Presentation< Word > const &p)
Return true if the -relation presentation can be strongly compressed.
void remove_duplicate_rules(Presentation< Word > &p)
Remove duplicate rules.
size_t length(Iterator first, Iterator last)
Return the sum of the lengths of all values in the range [first, last).
Presentation< Word >::letter_type first_unused_letter(Presentation< Word > const &p)
Return the first letter not in the alphabet of a presentation.
void add_rule(Presentation< Word > &p, Word const &lhop, Word const &rhop)
Add a rule to the presentation by reference and check.
Definition presentation.hpp:806
void throw_if_not_normalized(Presentation< Word > const &p, std::string_view arg="1st")
Throws if the presentation isn't normalized.
Definition presentation.hpp:696
void add_zero_rules(Presentation< Word > &p, typename Presentation< Word >::letter_type z)
Add rules for a zero element.
std::string to_gap_string(Presentation< word_type > const &p, std::string const &var_name)
Return the code that would create p in GAP.
Namespace containing some operators for creating words.
Definition word-range.hpp:2072
Namespace for everything in the libsemigroups library.
Definition action.hpp:44
T reverse(T... args)
T strlen(T... args)
Empty base for presentation-like classes.
Definition presentation.hpp:77
A stateless struct with binary call operator using shortlex_compare.
Definition order.hpp:356