Skip to content

Commit

Permalink
Merge human_readable_char and human_readable_letter
Browse files Browse the repository at this point in the history
  • Loading branch information
Joseph-Edwards committed Aug 14, 2024
1 parent 7279afb commit e21c294
Show file tree
Hide file tree
Showing 12 changed files with 92 additions and 123 deletions.
1 change: 1 addition & 0 deletions include/libsemigroups/knuth-bendix.tpp
Original file line number Diff line number Diff line change
Expand Up @@ -798,6 +798,7 @@ namespace libsemigroups {
return detail::internal_string_type({uint_to_internal_char(i)});
}

// TODO (later) replace with ToWord somehow?
template <typename Rewriter, typename ReductionOrder>
word_type KnuthBendix<Rewriter, ReductionOrder>::internal_string_to_word(
detail::internal_string_type const& s) {
Expand Down
4 changes: 2 additions & 2 deletions include/libsemigroups/presentation.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -1694,8 +1694,8 @@ namespace libsemigroups {
//! \throws LibsemigroupsException if `i` exceeds the number of letters in
//! supported by `letter_type`.
// TODO(later) move to words.*pp
template <typename Word>
typename Presentation<Word>::letter_type human_readable_letter(size_t i);
// template <typename Word>
// typename Presentation<Word>::letter_type human_readable_letter(size_t i);

//! \brief Return the first letter **not** in the alphabet of a
//! presentation.
Expand Down
20 changes: 1 addition & 19 deletions include/libsemigroups/presentation.tpp
Original file line number Diff line number Diff line change
Expand Up @@ -88,9 +88,7 @@ namespace libsemigroups {
n);
}
word_type lphbt(n, 0);
std::iota(lphbt.begin(),
lphbt.end(),
presentation::human_readable_letter<Word>(0));
std::iota(lphbt.begin(), lphbt.end(), human_readable_letter<Word>(0));

return alphabet(lphbt);
}
Expand Down Expand Up @@ -772,22 +770,6 @@ namespace libsemigroups {
remove_trivial_rules(p);
}

template <typename Word>
typename Presentation<Word>::letter_type human_readable_letter(size_t i) {
if constexpr (!std::is_same_v<Word, std::string>) {
using letter_type = typename Presentation<Word>::letter_type;
if (i >= std::numeric_limits<letter_type>::max()) {
LIBSEMIGROUPS_EXCEPTION(
"expected the argument to be in the range [0, {}), found {}",
std::numeric_limits<letter_type>::max(),
i);
}
return static_cast<letter_type>(i);
} else {
return human_readable_char(i);
}
}

template <typename Word>
typename Presentation<Word>::letter_type
first_unused_letter(Presentation<Word> const& p) {
Expand Down
12 changes: 4 additions & 8 deletions include/libsemigroups/to-presentation.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -108,10 +108,8 @@ namespace libsemigroups {
//!
//! If the alphabet of of \p p is \f$\{a_0, a_1, \dots a_{n-1}\}\f$, then the
//! conversion from `Presentation<WordInput>::letter_type` to
//! `Presentation<WordOutput>::letter_type` is either:
//! * \f$a_i \mapsto\f$ `human_readable_char(size_t i)` if `WordOutput` is
//! `std::string`; or
//! * \f$a_i \mapsto\f$ `i` otherwise.
//! `Presentation<WordOutput>::letter_type` is \f$a_i \mapsto\f$
//! `human_readable_letter<WordOutput>(size_t i)`.
//!
//! \tparam WordOutput the type of the words in the returned presentation.
//! \tparam WordInput the type of the words in the input presentation.
Expand Down Expand Up @@ -215,10 +213,8 @@ namespace libsemigroups {
//!
//! If the alphabet of of \p ip is \f$\{a_0, a_1, \dots a_{n-1}\}\f$, then the
//! conversion from `InversePresentation<WordInput>::letter_type` to
//! `InversePresentation<WordOutput>::letter_type` is either:
//! * \f$a_i \mapsto\f$ `human_readable_char(size_t i)` if `WordOutput` is
//! `std::string`; or
//! * \f$a_i \mapsto\f$ `i` otherwise.
//! `InversePresentation<WordOutput>::letter_type` is \f$a_i \mapsto\f$
//! `human_readable_letter<WordOutput>(size_t i)`.
//!
//! \tparam WordOutput the type of the words in the returned inverse
//! presentation.
Expand Down
8 changes: 3 additions & 5 deletions include/libsemigroups/to-presentation.tpp
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,7 @@ namespace libsemigroups {
Presentation<WordOutput> p;
p.alphabet(fp.number_of_generators());
WordOutput lhs, rhs;
auto f = [](auto val) {
return presentation::human_readable_letter<WordOutput>(val);
};
auto f = [](auto val) { return human_readable_letter<WordOutput>(val); };

for (auto it = fp.cbegin_rules(); it != fp.cend_rules(); ++it) {
lhs.resize(it->first.size());
Expand Down Expand Up @@ -77,7 +75,7 @@ namespace libsemigroups {
-> std::enable_if_t<!std::is_same_v<WordOutput, WordInput>,
Presentation<WordOutput>> {
return to_presentation<WordOutput>(p, [&p](auto val) {
return presentation::human_readable_letter<WordOutput>(p.index(val));
return human_readable_letter<WordOutput>(p.index(val));
});
}

Expand Down Expand Up @@ -118,7 +116,7 @@ namespace libsemigroups {
-> std::enable_if_t<!std::is_same_v<WordOutput, WordInput>,
InversePresentation<WordOutput>> {
return to_inverse_presentation<WordOutput>(ip, [&ip](auto val) {
return presentation::human_readable_letter<WordOutput>(ip.index(val));
return human_readable_letter<WordOutput>(ip.index(val));
});
}
} // namespace libsemigroups
43 changes: 33 additions & 10 deletions include/libsemigroups/words.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -711,7 +711,7 @@ namespace libsemigroups {
//!
//! Defined in `words.hpp`.
//!
//! This function is the inverse of \ref human_readable_char, see the
//! This function is the inverse of \ref human_readable_letter, see the
//! documentation of that function for more details.
//!
//! \param c character whose index is sought.
Expand All @@ -721,7 +721,7 @@ namespace libsemigroups {
//! \exception
//! \no_libsemigroups_except
//!
//! \sa human_readable_char
//! \sa human_readable_letter
[[nodiscard]] letter_type human_readable_index(char c);

//! \ingroup words_group
Expand Down Expand Up @@ -1003,6 +1003,10 @@ namespace libsemigroups {
// Words -> Strings
////////////////////////////////////////////////////////////////////////

namespace detail {
std::string const& chars_in_human_readable_order();
}

//! \ingroup words_group
//! \brief Returns a character by index in human readable order.
//!
Expand All @@ -1020,7 +1024,25 @@ namespace libsemigroups {
//! \returns A value of type \c char.
//!
//! \throws LibsemigroupsException if \p i exceeds the number of characters.
[[nodiscard]] char human_readable_char(size_t i);
template <typename Word = std::string>
typename Word::value_type human_readable_letter(size_t i) {
if (i >= std::numeric_limits<typename Word::value_type>::max()
- std::numeric_limits<typename Word::value_type>::min()) {
LIBSEMIGROUPS_EXCEPTION(
"expected the argument to be in the range [0, {}), found {}",
std::numeric_limits<typename Word::value_type>::max(),
i);
}
if constexpr (!std::is_same_v<Word, std::string>) {
return static_cast<typename Word::value_type>(i);
} else {
// Choose visible characters a-zA-Z0-9 first before anything else
// The ascii ranges for these characters are: [97, 123), [65, 91),
// [48, 58) so the remaining range of chars that are appended to the end
// after these chars are [0,48), [58, 65), [91, 97), [123, 255)
return detail::chars_in_human_readable_order()[i];
}
}

//! \ingroup words_group
//! \brief Class for converting \ref word_type into std::string with specified
Expand All @@ -1031,7 +1053,8 @@ namespace libsemigroups {
//! An instance of this class is used to convert from \ref word_type to
//! std::string. The letters in the word are converted to characters
//! according to their position in alphabet used to construct a ToString
//! instance if one is provided, or using \ref human_readable_char otherwise.
//! instance if one is provided, or using \ref human_readable_letter
//! otherwise.
//!
//! \par Example
//! \code
Expand Down Expand Up @@ -1138,7 +1161,7 @@ namespace libsemigroups {
//! This function converts its second argument \p input into a std::string
//! and stores the result in the first argument \p output. The characters of
//! \p input are converted using the alphabet used to construct the object
//! or set via init(), or with \ref human_readable_char if \ref empty
//! or set via init(), or with \ref human_readable_letter if \ref empty
//! returns `true`.
//!
//! The contents of the first argument \p output, if any, is removed.
Expand All @@ -1159,8 +1182,8 @@ namespace libsemigroups {
//!
//! This function converts its argument \p input into a std::string. The
//! characters of \p input are converted using the alphabet used to
//! construct the object or set via init(), or with \ref human_readable_char
//! if \ref empty returns `true`.
//! construct the object or set via init(), or with \ref
//! human_readable_letter if \ref empty returns `true`.
//!
//! \param input the \ref word_type to convert.
//!
Expand All @@ -1182,7 +1205,7 @@ namespace libsemigroups {
//! This function converts its second argument \p input into a std::string
//! and stores the result in the first argument \p output. The characters of
//! \p input are converted using the alphabet used to construct the object
//! or set via init(), or with \ref human_readable_char if \ref empty
//! or set via init(), or with \ref human_readable_letter if \ref empty
//! returns `true`.
//!
//! The contents of the first argument \p output, if any, is removed.
Expand All @@ -1202,8 +1225,8 @@ namespace libsemigroups {
//!
//! This function converts its argument \p input into a std::string. The
//! characters of \p input are converted using the alphabet used to
//! construct the object or set via init(), or with \ref human_readable_char
//! if \ref empty returns `true`.
//! construct the object or set via init(), or with \ref
//! human_readable_letter if \ref empty returns `true`.
//!
//! \param input the string to convert.
//!
Expand Down
8 changes: 4 additions & 4 deletions src/presentation.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@

#include "libsemigroups/exception.hpp" // for LIBSEMIGROUPS_EXCEPTION
#include "libsemigroups/presentation.hpp" // for Presentation, to_string, to_word
#include "libsemigroups/to-presentation.hpp" // for human_readable_char
#include "libsemigroups/to-presentation.hpp" // for to_presentation
#include "libsemigroups/types.hpp" // for word_type
#include "libsemigroups/words.hpp" // for human_readable_char
#include "libsemigroups/words.hpp" // for human_readable_letter

#include "libsemigroups/detail/fmt.hpp" // for format

Expand Down Expand Up @@ -77,7 +77,7 @@ namespace libsemigroups {
std::string out;
std::string sep = "";
for (auto it = w.cbegin(); it < w.cend(); ++it) {
out += sep + human_readable_char(*it);
out += sep + human_readable_letter<>(*it);
sep = " * ";
}
return out;
Expand All @@ -92,7 +92,7 @@ namespace libsemigroups {

std::string sep = "";
for (auto it = p.alphabet().cbegin(); it != p.alphabet().cend(); ++it) {
out += fmt::format("{}\"{}\"", sep, human_readable_char(*it));
out += fmt::format("{}\"{}\"", sep, human_readable_letter<>(*it));
sep = ", ";
}
out += ");\n";
Expand Down
24 changes: 4 additions & 20 deletions src/words.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,7 @@ namespace libsemigroups {
// 2. Strings -> Words
////////////////////////////////////////////////////////////////////////

namespace {
namespace detail {
std::string const& chars_in_human_readable_order() {
// Choose visible characters a-zA-Z0-9 first before anything else
// The ascii ranges for these characters are: [97, 123), [65, 91),
Expand Down Expand Up @@ -225,7 +225,7 @@ namespace libsemigroups {
}
return letters;
}
} // namespace
} // namespace detail

ToWord::ToWord(ToWord const&) = default;
ToWord::ToWord(ToWord&&) = default;
Expand All @@ -242,7 +242,7 @@ namespace libsemigroups {
map;
if (first_call) {
first_call = false;
auto const& chars = chars_in_human_readable_order();
auto const& chars = detail::chars_in_human_readable_order();
for (letter_type i = 0; i < chars.size(); ++i) {
map.emplace(chars[i], i);
}
Expand Down Expand Up @@ -328,22 +328,6 @@ namespace libsemigroups {
// 3. Words -> Strings
////////////////////////////////////////////////////////////////////////

char human_readable_char(size_t i) {
using letter_type_ = typename Presentation<std::string>::letter_type;
// Choose visible characters a-zA-Z0-9 first before anything else
// The ascii ranges for these characters are: [97, 123), [65, 91),
// [48, 58) so the remaining range of chars that are appended to the end
// after these chars are [0,48), [58, 65), [91, 97), [123, 255)
if (i >= std::numeric_limits<letter_type_>::max()
- std::numeric_limits<letter_type_>::min()) {
LIBSEMIGROUPS_EXCEPTION("expected a value in the range [0, {}) found {}",
std::numeric_limits<letter_type>::max()
- std::numeric_limits<letter_type>::min(),
i);
}
return chars_in_human_readable_order()[i];
}

ToString::ToString(ToString const&) = default;
ToString::ToString(ToString&&) = default;
ToString& ToString::operator=(ToString const&) = default;
Expand Down Expand Up @@ -374,7 +358,7 @@ namespace libsemigroups {
std::transform(input.cbegin(),
input.cend(),
output.begin(),
[](letter_type c) { return human_readable_char(c); });
[](letter_type c) { return human_readable_letter<>(c); });
} else { // Non-empty alphabet implies conversion should use the alphabet.
output.clear();
output.reserve(input.size());
Expand Down
Loading

0 comments on commit e21c294

Please sign in to comment.