From 0cbf8dedd1f330d468401fd4ac27d1aca7abb63b Mon Sep 17 00:00:00 2001 From: James Swent Date: Mon, 1 Dec 2025 22:31:27 +0000 Subject: [PATCH 1/2] order: add wt_shortlex_compare from libsemigroups --- docs/source/data-structures/order/index.rst | 2 + src/libsemigroups_pybind11/__init__.py | 1 + src/order.cpp | 53 +++++++++++++++++++++ 3 files changed, 56 insertions(+) diff --git a/docs/source/data-structures/order/index.rst b/docs/source/data-structures/order/index.rst index 2cd7ff38..e1b41f20 100644 --- a/docs/source/data-structures/order/index.rst +++ b/docs/source/data-structures/order/index.rst @@ -35,3 +35,5 @@ Full API .. autofunction:: recursive_path_compare .. autofunction:: shortlex_compare + +.. autofunction:: wt_shortlex_compare diff --git a/src/libsemigroups_pybind11/__init__.py b/src/libsemigroups_pybind11/__init__.py index 25bd333f..fe839352 100644 --- a/src/libsemigroups_pybind11/__init__.py +++ b/src/libsemigroups_pybind11/__init__.py @@ -99,6 +99,7 @@ shortlex_compare, side, tril, + wt_shortlex_compare, ) except ModuleNotFoundError as e: raise ModuleNotFoundError( diff --git a/src/order.cpp b/src/order.cpp index 1480d7ba..cbbb27bf 100644 --- a/src/order.cpp +++ b/src/order.cpp @@ -201,6 +201,59 @@ is based on the source code of :cite:`Holt2018aa`. R"pbdoc( :sig=(x: str | list[int], y: str | list[int]) -> bool: :only-document-once: +)pbdoc"); + + // No prefix because not in subpackage + m.def( + "wt_shortlex_compare", + [](std::string const& x, std::string const& y, + std::vector const& weights) { + return wt_shortlex_compare(x, y, weights); + }, + py::arg("x"), + py::arg("y"), + py::arg("weights"), + R"pbdoc( +:sig=(x: str | list[int], y: str | list[int], weights: list[int]) -> bool: +:only-document-once: +Compare two values of type :any:`str` or ``list[int]`` using weighted shortlex ordering. + +This function compares two objects using the weighted short-lex ordering. The +weight of a word is computed by adding up the weights of the letters in the +word, where the ith index of the weights vector corresponds to the weight of +the ith letter in the alphabet. Heavier words come later in the ordering than +all lighter words. Amongst words of equal weight, short-lex ordering is used. + +:param x: the first object for comparison. +:type x: str | list[int] + +:param y: the second object for comparison. +:type y: str | list[int] + +:param weights: the weights vector, where the ith index corresponds to the weight of the ith letter. +:type weights: list[int] + +:returns: The boolean value ``True`` if *x* is weighted short-lex less than *y*, and ``False`` otherwise. +:rtype: bool + +:raises LibsemigroupsError: if any letter in *x* or *y* is not a valid index into the weights vector. + +:complexity: At most :math:`O(n + m)` where :math:`n` is the length of *x* and :math:`m` is the length of *y*. +)pbdoc"); + + // No prefix because not in subpackage + m.def( + "wt_shortlex_compare", + [](word_type const& x, word_type const& y, + std::vector const& weights) { + return wt_shortlex_compare(x, y, weights); + }, + py::arg("x"), + py::arg("y"), + py::arg("weights"), + R"pbdoc( +:sig=(x: str | list[int], y: str | list[int], weights: list[int]) -> bool: +:only-document-once: )pbdoc"); } } // namespace libsemigroups From be27505e72bc2e5d61143c0fd738c3660bf459c0 Mon Sep 17 00:00:00 2001 From: James Swent Date: Mon, 1 Dec 2025 23:46:42 +0000 Subject: [PATCH 2/2] order: add wt_lex_compare from libsemigroups --- src/libsemigroups_pybind11/__init__.py | 1 + src/order.cpp | 61 +++++++++++++++++++++++++- 2 files changed, 60 insertions(+), 2 deletions(-) diff --git a/src/libsemigroups_pybind11/__init__.py b/src/libsemigroups_pybind11/__init__.py index fe839352..7db4950d 100644 --- a/src/libsemigroups_pybind11/__init__.py +++ b/src/libsemigroups_pybind11/__init__.py @@ -99,6 +99,7 @@ shortlex_compare, side, tril, + wt_lex_compare, wt_shortlex_compare, ) except ModuleNotFoundError as e: diff --git a/src/order.cpp b/src/order.cpp index cbbb27bf..822089bb 100644 --- a/src/order.cpp +++ b/src/order.cpp @@ -206,7 +206,8 @@ is based on the source code of :cite:`Holt2018aa`. // No prefix because not in subpackage m.def( "wt_shortlex_compare", - [](std::string const& x, std::string const& y, + [](std::string const& x, + std::string const& y, std::vector const& weights) { return wt_shortlex_compare(x, y, weights); }, @@ -244,7 +245,8 @@ all lighter words. Amongst words of equal weight, short-lex ordering is used. // No prefix because not in subpackage m.def( "wt_shortlex_compare", - [](word_type const& x, word_type const& y, + [](word_type const& x, + word_type const& y, std::vector const& weights) { return wt_shortlex_compare(x, y, weights); }, @@ -254,6 +256,61 @@ all lighter words. Amongst words of equal weight, short-lex ordering is used. R"pbdoc( :sig=(x: str | list[int], y: str | list[int], weights: list[int]) -> bool: :only-document-once: +)pbdoc"); + + // No prefix because not in subpackage + m.def( + "wt_lex_compare", + [](std::string const& x, + std::string const& y, + std::vector const& weights) { + return wt_lex_compare(x, y, weights); + }, + py::arg("x"), + py::arg("y"), + py::arg("weights"), + R"pbdoc( +:sig=(x: str | list[int], y: str | list[int], weights: list[int]) -> bool: +:only-document-once: +Compare two values of type :any:`str` or ``list[int]`` using weighted lex ordering. + +This function compares two objects using the weighted lex ordering. The +weight of a word is computed by adding up the weights of the letters in the +word, where the ith index of the weights vector corresponds to the weight of +the ith letter in the alphabet. Heavier words come later in the ordering than +all lighter words. Amongst words of equal weight, lexicographic ordering is used. + +:param x: the first object for comparison. +:type x: str | list[int] + +:param y: the second object for comparison. +:type y: str | list[int] + +:param weights: the weights vector, where the ith index corresponds to the weight of the ith letter. +:type weights: list[int] + +:returns: The boolean value ``True`` if *x* is weighted lex less than *y*, and ``False`` otherwise. +:rtype: bool + +:raises LibsemigroupsError: if any letter in *x* or *y* is not a valid index into the weights vector. + +:complexity: At most :math:`O(n + m)` where :math:`n` is the length of *x* and :math:`m` is the length of *y*. +)pbdoc"); + + // No prefix because not in subpackage + m.def( + "wt_lex_compare", + [](word_type const& x, + word_type const& y, + std::vector const& weights) { + return wt_lex_compare(x, y, weights); + }, + py::arg("x"), + py::arg("y"), + py::arg("weights"), + R"pbdoc( +:sig=(x: str | list[int], y: str | list[int], weights: list[int]) -> bool: +:only-document-once: )pbdoc"); } } // namespace libsemigroups