Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixed the doc sets/recursively_enumerated_set.py #37331

Merged
merged 11 commits into from
Mar 25, 2024
102 changes: 41 additions & 61 deletions src/sage/sets/recursively_enumerated_set.pyx
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,11 @@ sets that are described by some ``seeds`` and a successor function
graded, forest) or not. The elements of a set having a symmetric, graded or
forest structure can be enumerated uniquely without keeping all of them in
memory. Many kinds of iterators are provided in this module: depth first
search, breadth first search or elements of given depth.
search, breadth first search and elements of given depth.

See :wikipedia:`Recursively_enumerable_set`.

See documentation of :func:`RecursivelyEnumeratedSet` below for the
See the documentation of :func:`RecursivelyEnumeratedSet` below for the
description of the inputs.

AUTHORS:
Expand All @@ -27,7 +27,7 @@ No hypothesis on the structure

What we mean by "no hypothesis" is that the set is not known
to be a forest, symmetric, or graded. However, it may have other
structure, like not containing an oriented cycle, that does not
structure, such as not containing an oriented cycle, that does not
help with the enumeration.

In this example, the seed is 0 and the successor function is either ``+2``
Expand Down Expand Up @@ -140,8 +140,10 @@ Graded components (set of elements of the same depth)::
Forest structure
----------------

.. RUBRIC:: Forest structure [Ex 1]

The set of words over the alphabet `\{a,b\}` can be generated from the
empty word by appending letter `a` or `b` as a successor function. This set
empty word by appending the letter `a` or `b` as a successor function. This set
has a forest structure::

sage: seeds = ['']
Expand All @@ -162,9 +164,6 @@ Breadth first search iterator::
sage: [next(it) for _ in range(6)]
['', 'a', 'b', 'aa', 'ab', 'ba']

Example: Forest structure
-------------------------

This example was provided by Florent Hivert.

How to define a set using those classes?
Expand All @@ -175,41 +174,23 @@ classes being very similar):

.. MATH::

\begin{picture}(-300,0)(600,0)
% Root
\put(0,0){\circle*{7}}
\put(0,10){\makebox(0,10){``\ ''}}
% First Children
\put(-150,-60){\makebox(0,10){``a''}}
\put(0,-60){\makebox(0,10){``b''}}
\put(150,-60){\makebox(0,10){``c''}}
\multiput(-150,-70)(150,0){3}{\circle*{7}}
% Second children
\put(-200,-130){\makebox(0,10){``aa''}}
\put(-150,-130){\makebox(0,10){``ab''}}
\put(-100,-130){\makebox(0,10){``ac''}}
\put(-50,-130){\makebox(0,10){``ba''}}
\put(0,-130){\makebox(0,10){``bb''}}
\put(50,-130){\makebox(0,10){``bc''}}
\put(100,-130){\makebox(0,10){``ca''}}
\put(150,-130){\makebox(0,10){``cb''}}
\put(200,-130){\makebox(0,10){``cc''}}
\multiput(-200,-140)(50,0){9}{\circle*{7}}
% Legend
\put(100,-5){\makebox(0,10)[l]{1) An initial element}}
\put(-250,-5){\makebox(0,10)[l]{2) A function of an element enumerating}}
\put(-235,-20){\makebox(0,10)[l]{its children (if any)}}
% Arrows
\thicklines
\put(0,-10){\vector(0,-1){30}}
\put(-15,-5){\vector(-2,-1){110}}
\put(15,-5){\vector(2,-1){110}}
\multiput(-150,-80)(150,0){3}{\vector(0,-1){30}}
\multiput(-160,-80)(150,0){3}{\vector(-1,-1){30}}
\multiput(-140,-80)(150,0){3}{\vector(1,-1){30}}
\put(90,0){\vector(-1,0){70}}
\put(-215,-30){\vector(1,-1){40}}
\end{picture}
\begin{array}{ccc}
& ``\," \\
\hfil\swarrow & \downarrow & \searrow\hfil\\
``a" & ``b" & ``c" \\
\begin{array}{ccc}
\swarrow & \downarrow & \searrow \\
``aa" & ``ab" & ``ac" \\
\end{array} &
\begin{array}{ccc}
\swarrow & \downarrow & \searrow \\
``ba" & ``bb" & ``bc" \\
\end{array} &
\begin{array}{ccc}
\swarrow & \downarrow & \searrow \\
``ca" & ``cb" & ``cc" \\
\end{array}
\end{array}

For the previous example, the two necessary pieces of information are:

Expand All @@ -219,7 +200,7 @@ For the previous example, the two necessary pieces of information are:

lambda x: [x + letter for letter in ['a', 'b', 'c']

This would actually describe an **infinite** set, as such rules describes
This would actually describe an **infinite** set, as such rules describe
"all words" on 3 letters. Hence, it is a good idea to replace the function by::

lambda x: [x + letter for letter in ['a', 'b', 'c']] if len(x) < 2 else []
Expand Down Expand Up @@ -249,14 +230,13 @@ or::
sage: S.list()
['', 'a', 'aa', 'ab', 'ac', 'b', 'ba', 'bb', 'bc', 'c', 'ca', 'cb', 'cc']

Example: Forest structure 2
---------------------------
.. RUBRIC:: Forest structure [Ex 2]

This example was provided by Florent Hivert.

Here is a little more involved example. We want to iterate through all
permutations of a given set `S`. One solution is to take elements of `S` one
by one an insert them at every positions. So a node of the generating tree
by one and insert them at every position. So a node of the generating tree
contains two pieces of information:

- the list ``lst`` of already inserted element;
Expand Down Expand Up @@ -320,7 +300,7 @@ def RecursivelyEnumeratedSet(seeds, successors, structure=None,

A set `S` is called recursively enumerable if there is an algorithm that
enumerates the members of `S`. We consider here the recursively
enumerated set that are described by some ``seeds`` and a successor
enumerated sets that are described by some ``seeds`` and a successor
function ``successors``.

Let `U` be a set and ``successors`` `:U \to 2^U` be a successor function
Expand Down Expand Up @@ -406,7 +386,7 @@ def RecursivelyEnumeratedSet(seeds, successors, structure=None,

.. WARNING::

If you do not set the good structure, you might obtain bad results,
If you do not set a good structure, you might obtain bad results,
janmenjayap marked this conversation as resolved.
Show resolved Hide resolved
like elements generated twice::

sage: f = lambda a: [a-1,a+1]
Expand Down Expand Up @@ -781,8 +761,8 @@ cdef class RecursivelyEnumeratedSet_generic(Parent):
r"""
Iterate over the elements of ``self`` of given depth.

An element of depth `n` can be obtained applying `n` times the
successor function to a seed.
An element of depth `n` can be obtained by applying the
successor function `n` times to a seed.

INPUT:

Expand Down Expand Up @@ -847,7 +827,7 @@ cdef class RecursivelyEnumeratedSet_generic(Parent):
r"""
Iterate on the elements of ``self`` (breadth first).

This code remembers every elements generated and uses python
This code remembers every element generated and uses python
queues. It is 3 times slower than the other one.

See :wikipedia:`Breadth-first_search`.
Expand Down Expand Up @@ -876,7 +856,7 @@ cdef class RecursivelyEnumeratedSet_generic(Parent):
r"""
Iterate on the elements of ``self`` (in no particular order).

This code remembers every elements generated.
This code remembers every element generated.

TESTS:

Expand Down Expand Up @@ -905,7 +885,7 @@ cdef class RecursivelyEnumeratedSet_generic(Parent):
r"""
Iterate on the elements of ``self`` (depth first).

This code remembers every elements generated.
This code remembers every element generated.

The elements are traversed right-to-left, so the last element returned
by the successor function is visited first.
Expand Down Expand Up @@ -1552,7 +1532,7 @@ def search_forest_iterator(roots, children, algorithm='depth'):
[0, 0, 0], [0, 0, 1], [0, 1, 0], [0, 1, 1],
[1, 0, 0], [1, 0, 1], [1, 1, 0], [1, 1, 1]]

This allows for iterating trough trees of infinite depth::
This allows for iterating through trees of infinite depth::

sage: it = search_forest_iterator([[]], lambda l: [l+[0], l+[1]], algorithm='breadth')
sage: [ next(it) for i in range(16) ]
Expand All @@ -1574,9 +1554,9 @@ def search_forest_iterator(roots, children, algorithm='depth'):
[0, 1, 2], [0, 2, 1], [1, 0, 2], [1, 2, 0], [2, 0, 1], [2, 1, 0]]
"""
# Little trick: the same implementation handles both depth and
# breadth first search. Setting position to -1 makes a depth search
# breadth first search. Setting position to -1 results in a depth search
# (you ask the children for the last node you met). Setting
# position on 0 makes a breadth search (enumerate all the
# position on 0 results in a breadth search (enumerate all the
# descendants of a node before going on to the next father)
if algorithm == 'depth':
position = -1
Expand Down Expand Up @@ -1920,8 +1900,8 @@ class RecursivelyEnumeratedSet_forest(Parent):
def _elements_of_depth_iterator_rec(self, depth=0):
r"""
Return an iterator over the elements of ``self`` of given depth.
An element of depth `n` can be obtained applying `n` times the
children function from a root. This function is not affected
An element of depth `n` can be obtained by applying the
children function `n` times from a root. This function is not affected
by post processing.

EXAMPLES::
Expand Down Expand Up @@ -1951,8 +1931,8 @@ class RecursivelyEnumeratedSet_forest(Parent):
def elements_of_depth_iterator(self, depth=0):
r"""
Return an iterator over the elements of ``self`` of given depth.
An element of depth `n` can be obtained applying `n` times the
children function from a root.
An element of depth `n` can be obtained by applying the
children function `n` times from a root.

EXAMPLES::

Expand Down Expand Up @@ -2010,7 +1990,7 @@ class RecursivelyEnumeratedSet_forest(Parent):
depth first search and breadth first search failed. The
following example enumerates all ordered pairs of nonnegative
integers, starting from an infinite set of roots, where each
roots has an infinite number of children::
root has an infinite number of children::

sage: from sage.sets.recursively_enumerated_set import RecursivelyEnumeratedSet_forest
sage: S = RecursivelyEnumeratedSet_forest(Family(NN, lambda x : (x, 0)),
Expand Down
Loading