Projects
openEuler:Mainline
python-more-itertools
Sign Up
Log In
Username
Password
We truncated the diff of some files because they were too big. If you want to see the full diff for every file,
click here
.
Overview
Repositories
Revisions
Requests
Users
Attributes
Meta
Expand all
Collapse all
Changes of Revision 4
View file
_service:tar_scm:python-more-itertools.spec
Changed
@@ -1,5 +1,5 @@ Name: python-more-itertools -Version: 8.12.0 +Version: 9.1.0 Release: 1 Summary: An opensource python library wrapping around itertools License: MIT @@ -15,6 +15,8 @@ %package -n python3-more-itertools Summary: An opensource python library wrapping around itertools BuildRequires: python3-devel python3-six +BuildRequires: python3-pip python3-wheel +BuildRequires: python3-flit-core %{?python_provide:%python_provide python3-more-itertools} %description -n python3-more-itertools @@ -26,21 +28,24 @@ %autosetup -n more-itertools-%{version} -p1 %build -%py3_build +%pyproject_build %install -%py3_install +%pyproject_install %check -%{__python3} ./setup.py test +export PYTHONPATH=%{buildroot}%{python3_sitelib} +%{__python3} -m unittest -v %files -n python3-more-itertools %doc README.rst LICENSE %{python3_sitelib}/more_itertools/ -%exclude %{python3_sitelib}/more_itertools/tests -%{python3_sitelib}/more_itertools-%{version}-py%{python3_version}.egg-info +%{python3_sitelib}/more_itertools-%{version}*-info %changelog +* Wed Jun 07 2023 yaoxin <yao_xin001@hoperun.com> - 9.1.0-1 +- Update to 9.1.0 + * Thu Jul 7 2022 wulei <wulei80@h-partners.com> - 8.12.0-1 - Upgrade to 8.12.0
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/.
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/.github
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/.github/ISSUE_TEMPLATE
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/.github/workflows
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/docs
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/docs/_static
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/tests
Deleted
-(directory)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/.github/workflows/python-app.yml -> _service:tar_scm:more-itertools-9.1.0.tar.gz/.github/workflows/python-app.yml
Changed
@@ -8,12 +8,12 @@ runs-on: ubuntu-latest strategy: matrix: - python-version: 3.6, 3.7, 3.8, 3.9.0, 3.10.0, pypy3 + python-version: "3.7", "3.8", "3.9", "3.10", "3.11", "3.12.0-alpha.1", "pypy-3.8" steps: - - uses: actions/checkout@v2 + - uses: actions/checkout@v3 - name: Set up Python ${{ matrix.python-version }} - uses: actions/setup-python@v2 + uses: actions/setup-python@v4 with: python-version: ${{ matrix.python-version }} - name: Install dependencies @@ -31,28 +31,28 @@ run: | flake8 . - name: Check formatting with black - if: "matrix.python-version == '3.6'" + if: "matrix.python-version == '3.7'" run: | pip install -U black black --check . - name: Check type stubs with mypy - if: "matrix.python-version != 'pypy3'" + if: "matrix.python-version != 'pypy-3.8'" run: | pip install -U mypy stubtest more_itertools.more more_itertools.recipes - name: Build docs with sphinx - if: "matrix.python-version == '3.6'" + if: "matrix.python-version == '3.7'" run: | pip install -U sphinx sphinx_rtd_theme sphinx-build -W -b html docs docs/_build/html - name: Build packages - if: "matrix.python-version == '3.6'" + if: "matrix.python-version == '3.7'" run: | - pip install -U twine wheel - python setup.py sdist bdist_wheel + pip install -U flit twine + flit build --setup-py twine check dist/* - name: Upload packages - if: "matrix.python-version == '3.6'" + if: "matrix.python-version == '3.7'" uses: actions/upload-artifact@v2 with: name: more-itertools-packages
View file
_service:tar_scm:more-itertools-9.1.0.tar.gz/PKG-INFO
Added
@@ -0,0 +1,246 @@ +Metadata-Version: 2.1 +Name: more-itertools +Version: 9.1.0 +Summary: More routines for operating on iterables, beyond itertools +Keywords: itertools,iterator,iteration,filter,peek,peekable,chunk,chunked +Author-email: Erik Rose <erikrose@grinchcentral.com> +Requires-Python: >=3.7 +Description-Content-Type: text/x-rst +Classifier: Development Status :: 5 - Production/Stable +Classifier: Intended Audience :: Developers +Classifier: Natural Language :: English +Classifier: License :: OSI Approved :: MIT License +Classifier: Programming Language :: Python :: 3 +Classifier: Programming Language :: Python :: 3.7 +Classifier: Programming Language :: Python :: 3.8 +Classifier: Programming Language :: Python :: 3.9 +Classifier: Programming Language :: Python :: 3.10 +Classifier: Programming Language :: Python :: 3.11 +Classifier: Programming Language :: Python :: 3 :: Only +Classifier: Programming Language :: Python :: Implementation :: CPython +Classifier: Programming Language :: Python :: Implementation :: PyPy +Classifier: Topic :: Software Development :: Libraries +Project-URL: Homepage, https://github.com/more-itertools/more-itertools + +============== +More Itertools +============== + +.. image:: https://readthedocs.org/projects/more-itertools/badge/?version=latest + :target: https://more-itertools.readthedocs.io/en/stable/ + +Python's ``itertools`` library is a gem - you can compose elegant solutions +for a variety of problems with the functions it provides. In ``more-itertools`` +we collect additional building blocks, recipes, and routines for working with +Python iterables. + ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Grouping | `chunked <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.chunked>`_, | +| | `ichunked <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.ichunked>`_, | +| | `chunked_even <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.chunked_even>`_, | +| | `sliced <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sliced>`_, | +| | `constrained_batches <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.constrained_batches>`_, | +| | `distribute <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distribute>`_, | +| | `divide <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.divide>`_, | +| | `split_at <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_at>`_, | +| | `split_before <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_before>`_, | +| | `split_after <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_after>`_, | +| | `split_into <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_into>`_, | +| | `split_when <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_when>`_, | +| | `bucket <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.bucket>`_, | +| | `unzip <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unzip>`_, | +| | `batched <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.batched>`_, | +| | `grouper <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.grouper>`_, | +| | `partition <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.partition>`_ | +| | `transpose <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.transpose>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Lookahead and lookback | `spy <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.spy>`_, | +| | `peekable <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.peekable>`_, | +| | `seekable <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.seekable>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Windowing | `windowed <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.windowed>`_, | +| | `substrings <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.substrings>`_, | +| | `substrings_indexes <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.substrings_indexes>`_, | +| | `stagger <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.stagger>`_, | +| | `windowed_complete <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.windowed_complete>`_, | +| | `pairwise <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.pairwise>`_, | +| | `triplewise <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.triplewise>`_, | +| | `sliding_window <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sliding_window>`_, | +| | `subslices <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.subslices>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Augmenting | `count_cycle <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.count_cycle>`_, | +| | `intersperse <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.intersperse>`_, | +| | `padded <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.padded>`_, | +| | `repeat_each <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeat_each>`_, | +| | `mark_ends <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.mark_ends>`_, | +| | `repeat_last <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeat_last>`_, | +| | `adjacent <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.adjacent>`_, | +| | `groupby_transform <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.groupby_transform>`_, | +| | `pad_none <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.pad_none>`_, | +| | `ncycles <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.ncycles>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Combining | `collapse <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.collapse>`_, | +| | `sort_together <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sort_together>`_, | +| | `interleave <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.interleave>`_, | +| | `interleave_longest <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.interleave_longest>`_, | +| | `interleave_evenly <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.interleave_evenly>`_, | +| | `zip_offset <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.zip_offset>`_, | +| | `zip_equal <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.zip_equal>`_, | +| | `zip_broadcast <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.zip_broadcast>`_, | +| | `dotproduct <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.dotproduct>`_, | +| | `convolve <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.convolve>`_, | +| | `flatten <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.flatten>`_, | +| | `roundrobin <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.roundrobin>`_, | +| | `prepend <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.prepend>`_, | +| | `value_chain <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.value_chain>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Summarizing | `ilen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.ilen>`_, | +| | `unique_to_each <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unique_to_each>`_, | +| | `sample <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sample>`_, | +| | `consecutive_groups <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.consecutive_groups>`_, | +| | `run_length <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.run_length>`_, | +| | `map_reduce <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.map_reduce>`_, | +| | `exactly_n <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.exactly_n>`_, | +| | `is_sorted <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.is_sorted>`_, | +| | `all_equal <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.all_equal>`_, | +| | `all_unique <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.all_unique>`_, | +| | `minmax <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.minmax>`_, | +| | `first_true <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.first_true>`_, | +| | `quantify <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.quantify>`_, | +| | `iequals <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iequals>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Selecting | `islice_extended <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.islice_extended>`_, | +| | `first <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.first>`_, | +| | `last <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.last>`_, | +| | `one <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.one>`_, | +| | `only <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.only>`_, | +| | `strictly_n <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.strictly_n>`_, | +| | `strip <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.strip>`_, | +| | `lstrip <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.lstrip>`_, | +| | `rstrip <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.rstrip>`_, | +| | `filter_except <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.filter_except>`_, | +| | `map_except <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.map_except>`_, | +| | `nth_or_last <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.nth_or_last>`_, | +| | `unique_in_window <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unique_in_window>`_, | +| | `before_and_after <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.before_and_after>`_, | +| | `nth <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.nth>`_, | +| | `take <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.take>`_, | +| | `tail <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.tail>`_, | +| | `unique_everseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertoo ls.unique_everseen>`_, | +| | `unique_justseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unique_justseen>`_, | +| | `duplicates_everseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.duplicates_everseen>`_, | +| | `duplicates_justseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.duplicates_justseen>`_, | +| | `longest_common_prefix <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.longest_common_prefix>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Combinatorics | `distinct_permutations <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distinct_permutations>`_, | +| | `distinct_combinations <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distinct_combinations>`_, | +| | `circular_shifts <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.circular_shifts>`_, | +| | `partitions <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.partitions>`_, | +| | `set_partitions <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.set_partitions>`_, | +| | `product_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.product_index>`_, | +| | `combination_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.combination_index>`_, | +| | `permutation_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.permutation_index>`_, | +| | `gray_product <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.gray_product>`_, | +| | `powerset <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.powerset>`_, | +| | `random_product <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_product>`_, | +| | `random_permutation <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_permutation>`_, | +| | `random_combination <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_combination>`_, | +| | `random_combination_with_replacement <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_combination_with_replacement>`_, | +| | `nth_product <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.nth_product>`_, | +| | `nth_permutation <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.nth_permutation>`_, | +| | `nth_combination <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.nth_combination>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Wrapping | `always_iterable <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.always_iterable>`_, | +| | `always_reversible <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.always_reversible>`_, | +| | `countable <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.countable>`_, | +| | `consumer <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.consumer>`_, | +| | `with_iter <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.with_iter>`_, | +| | `iter_except <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iter_except>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ +| Others | `locate <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.locate>`_, | +| | `rlocate <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.rlocate>`_, | +| | `replace <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.replace>`_, | +| | `numeric_range <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.numeric_range>`_, | +| | `side_effect <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.side_effect>`_, | +| | `iterate <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iterate>`_, | +| | `difference <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.difference>`_, | +| | `make_decorator <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.make_decorator>`_, | +| | `SequenceView <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.SequenceView>`_, | +| | `time_limited <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.time_limited>`_, | +| | `map_if <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.map_if>`_, | +| | `iter_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iter_index>`_, | +| | `consume <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.consume>`_, | +| | `tabulate <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.tabulate>`_, | +| | `repeatfunc <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeatfunc>`_, | +| | `polynomial_from_roots <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.polynomial_from_roots>`_, | +| | `sieve <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sieve>`_ | +| | `factor <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.factor>`_ | +| | `matmul <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.matmul>`_ | ++------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ + + +Getting started +=============== + +To get started, install the library with `pip <https://pip.pypa.io/en/stable/>`_: + +.. code-block:: shell + + pip install more-itertools + +The recipes from the `itertools docs <https://docs.python.org/3/library/itertools.html#itertools-recipes>`_ +are included in the top-level package: + +.. code-block:: python + + >>> from more_itertools import flatten + >>> iterable = (0, 1), (2, 3) + >>> list(flatten(iterable)) + 0, 1, 2, 3
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/README.rst -> _service:tar_scm:more-itertools-9.1.0.tar.gz/README.rst
Changed
@@ -13,7 +13,9 @@ +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ | Grouping | `chunked <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.chunked>`_, | | | `ichunked <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.ichunked>`_, | +| | `chunked_even <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.chunked_even>`_, | | | `sliced <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sliced>`_, | +| | `constrained_batches <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.constrained_batches>`_, | | | `distribute <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distribute>`_, | | | `divide <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.divide>`_, | | | `split_at <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_at>`_, | @@ -23,8 +25,10 @@ | | `split_when <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.split_when>`_, | | | `bucket <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.bucket>`_, | | | `unzip <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unzip>`_, | +| | `batched <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.batched>`_, | | | `grouper <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.grouper>`_, | | | `partition <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.partition>`_ | +| | `transpose <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.transpose>`_ | +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ | Lookahead and lookback | `spy <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.spy>`_, | | | `peekable <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.peekable>`_, | @@ -37,11 +41,13 @@ | | `windowed_complete <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.windowed_complete>`_, | | | `pairwise <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.pairwise>`_, | | | `triplewise <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.triplewise>`_, | -| | `sliding_window <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sliding_window>`_ | +| | `sliding_window <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sliding_window>`_, | +| | `subslices <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.subslices>`_ | +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ | Augmenting | `count_cycle <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.count_cycle>`_, | | | `intersperse <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.intersperse>`_, | | | `padded <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.padded>`_, | +| | `repeat_each <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeat_each>`_, | | | `mark_ends <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.mark_ends>`_, | | | `repeat_last <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeat_last>`_, | | | `adjacent <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.adjacent>`_, | @@ -76,7 +82,8 @@ | | `all_unique <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.all_unique>`_, | | | `minmax <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.minmax>`_, | | | `first_true <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.first_true>`_, | -| | `quantify <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.quantify>`_ | +| | `quantify <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.quantify>`_, | +| | `iequals <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iequals>`_ | +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ | Selecting | `islice_extended <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.islice_extended>`_, | | | `first <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.first>`_, | @@ -98,7 +105,8 @@ | | `unique_everseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertoo ls.unique_everseen>`_, | | | `unique_justseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.unique_justseen>`_, | | | `duplicates_everseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.duplicates_everseen>`_, | -| | `duplicates_justseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.duplicates_justseen>`_ | +| | `duplicates_justseen <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.duplicates_justseen>`_, | +| | `longest_common_prefix <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.longest_common_prefix>`_ | +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ | Combinatorics | `distinct_permutations <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distinct_permutations>`_, | | | `distinct_combinations <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.distinct_combinations>`_, | @@ -108,6 +116,7 @@ | | `product_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.product_index>`_, | | | `combination_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.combination_index>`_, | | | `permutation_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.permutation_index>`_, | +| | `gray_product <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.gray_product>`_, | | | `powerset <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.powerset>`_, | | | `random_product <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_product>`_, | | | `random_permutation <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.random_permutation>`_, | @@ -134,9 +143,15 @@ | | `make_decorator <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.make_decorator>`_, | | | `SequenceView <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.SequenceView>`_, | | | `time_limited <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.time_limited>`_, | +| | `map_if <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.map_if>`_, | +| | `iter_index <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.iter_index>`_, | | | `consume <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.consume>`_, | | | `tabulate <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.tabulate>`_, | -| | `repeatfunc <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeatfunc>`_ | +| | `repeatfunc <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.repeatfunc>`_, | +| | `polynomial_from_roots <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.polynomial_from_roots>`_, | +| | `sieve <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.sieve>`_ | +| | `factor <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.factor>`_ | +| | `matmul <https://more-itertools.readthedocs.io/en/stable/api.html#more_itertools.matmul>`_ | +------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------+ @@ -198,3 +213,9 @@ and `@bbayles <https://github.com/bbayles>`_, with help from `many others <https://github.com/more-itertools/more-itertools/graphs/contributors>`_. If you have a problem or suggestion, please file a bug or pull request in this repository. Thanks for contributing! + + +Version History +=============== + +The version history can be found in `documentation <https://more-itertools.readthedocs.io/en/stable/versions.html>`_.
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/docs/api.rst -> _service:tar_scm:more-itertools-9.1.0.tar.gz/docs/api.rst
Changed
@@ -17,6 +17,7 @@ .. autofunction:: ichunked .. autofunction:: chunked_even .. autofunction:: sliced +.. autofunction:: constrained_batches(iterable, max_size, max_count=None, get_len=len, strict=True) .. autofunction:: distribute .. autofunction:: divide .. autofunction:: split_at @@ -31,8 +32,10 @@ **Itertools recipes** +.. autofunction:: batched .. autofunction:: grouper .. autofunction:: partition +.. autofunction:: transpose Lookahead and lookback @@ -72,6 +75,7 @@ .. autofunction:: pairwise .. autofunction:: triplewise .. autofunction:: sliding_window +.. autofunction:: subslices Augmenting @@ -152,6 +156,7 @@ .. function:: minmax(iterable, *, key, default) .. autofunction:: minmax(arg1, arg2, *args, key) :noindex: +.. autofunction:: iequals ---- @@ -189,6 +194,7 @@ .. autofunction:: unique_in_window .. autofunction:: duplicates_everseen .. autofunction:: duplicates_justseen +.. autofunction:: longest_common_prefix ---- @@ -219,6 +225,7 @@ .. autofunction:: product_index .. autofunction:: combination_index .. autofunction:: permutation_index +.. autofunction:: gray_product ---- @@ -281,6 +288,11 @@ **Itertools recipes** +.. autofunction:: iter_index .. autofunction:: consume .. autofunction:: tabulate .. autofunction:: repeatfunc +.. autofunction:: polynomial_from_roots +.. autofunction:: sieve +.. autofunction:: factor +.. autofunction:: matmul
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/docs/requirements.txt -> _service:tar_scm:more-itertools-9.1.0.tar.gz/docs/requirements.txt
Changed
@@ -1,27 +1,1 @@ -# What we want -Sphinx==4.3.0 - -# What we get -alabaster==0.7.12 -Babel==2.9.1 -certifi==2021.10.8 -charset-normalizer==2.0.7 -docutils==0.17.1 -idna==3.3 -imagesize==1.3.0 -Jinja2==3.0.3 -MarkupSafe==2.0.1 -packaging==21.2 -Pygments==2.10.0 -pyparsing==2.4.7 -pytz==2021.3 -requests==2.26.0 -six==1.16.0 -snowballstemmer==2.2.0 -sphinxcontrib-applehelp==1.0.2 -sphinxcontrib-devhelp==1.0.2 -sphinxcontrib-htmlhelp==2.0.0 -sphinxcontrib-jsmath==1.0.1 -sphinxcontrib-qthelp==1.0.3 -sphinxcontrib-serializinghtml==1.1.5 -urllib3==1.26.7 +Sphinx
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/docs/versions.rst -> _service:tar_scm:more-itertools-9.1.0.tar.gz/docs/versions.rst
Changed
@@ -5,6 +5,75 @@ .. automodule:: more_itertools :noindex: +8.14.0 +------ + +* New functions + * :func:`iter_index` (from the Python itertools docs) + * :func:`transpose` (from the Python itertools docs) + * :func:`matmul` (from the Python itertools docs) + * :func:`factor` (from the Python itertools docs) + * :func:`gray_product` (thanks to haukex) + +* Changes to existing functions + * :func:`sieve` was updated to match the Python itertools docs + * :func:`maxsplit` was updated to fix a bug (thanks to abingham) + * :func:`sliced` had its `type hint <https://github.com/more-itertools/more-itertools/pull/667>`__ updated (thanks to ad-chaos) + + +* Other changes + * The ``batched`` function is marked as deprecated and will be removed in a future major release. For Python 3.12 and above, use ``itertools.batched`` instead. (thanks to neutrinoceros) + * The type hints now used postponed evaluation of annotations from PEP 563 (thanks to Isira-Seneviratne) + * Some documentation issues were fixed (thanks to Voskov and jdkandersson) + +9.0.0 +------ + +* Potentially breaking changes + * :func:`grouper` no longer accepts an integer as its first argument. Previously this raised a ``DeprecationWarning``. + * :func:`collate` has been removed. Use the built-in :func:`heapq.merge` instead. + * :func:`windowed` now yields nothing when its iterable is empty. + * This library now advertises support for Python 3.7+. + +* New functions + * :func:`constrained_batches` + * :func:`batched` (from the Python itertools docs) + * :func:`polynomial_from_roots` (from the Python itertools docs) + * :func:`sieve` (from the Python itertools docs) + +* Other changes + * Some documentation issues were fixed (thanks to nanouasyn) + +8.14.0 +------ + +* New functions + * :func:`longest_common_prefix` (thanks to nanouasyn) + * :func:`iequals` (thanks to nanouasyn) + +* Changes to existing functions + * `concurrent.futures.ThreadPoolExecutor` is now imported lazily in :func:`callback_iter`. + * :func:`tail` is now optimized for iterables with a fixed length. + +* Other changes + * Some documentation issues were fixed (thanks to pochmann and timgates42) + * This library is now marked for Python 3.10 compatibility in PyPI (thanks to chayim) + +8.13.0 +------ + +* New functions + * The :func:`subslices` recipe from the `itertools` docs was added (thanks to rhettinger) + +* Changes to existing functions + * The :func:`ichunked` function is now more efficient (thanks to hjtran0 and seanmacavaney) + * The :func:`difference` function is now more efficient (thanks to Masynchin) + * The :func:`grouper` recipe now has more features, mirroring the one in the `itertools` docs (thanks to rhettinger) + +* Other changes + * Some documentation issues were fixed (thanks to medvied and Freed-Wu) + * The `more_itertools` package is now built with `flit` (thanks to mgorny) + 8.12.0 ------
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools/__init__.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/more_itertools/__init__.py
Changed
@@ -1,4 +1,6 @@ +"""More routines for operating on iterables, beyond itertools""" + from .more import * # noqa from .recipes import * # noqa -__version__ = '8.12.0' +__version__ = '9.1.0'
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools/more.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/more_itertools/more.py
Changed
@@ -2,9 +2,8 @@ from collections import Counter, defaultdict, deque, abc from collections.abc import Sequence -from concurrent.futures import ThreadPoolExecutor from functools import partial, reduce, wraps -from heapq import merge, heapify, heapreplace, heappop +from heapq import heapify, heapreplace, heappop from itertools import ( chain, compress, @@ -27,12 +26,16 @@ from time import monotonic from .recipes import ( + _marker, + _zip_equal, + UnequalIterablesError, consume, flatten, pairwise, powerset, take, unique_everseen, + all_equal, ) __all__ = @@ -49,9 +52,9 @@ 'chunked_even', 'circular_shifts', 'collapse', - 'collate', 'combination_index', 'consecutive_groups', + 'constrained_batches', 'consumer', 'count_cycle', 'countable', @@ -65,8 +68,10 @@ 'exactly_n', 'filter_except', 'first', + 'gray_product', 'groupby_transform', 'ichunked', + 'iequals', 'ilen', 'interleave', 'interleave_evenly', @@ -77,6 +82,7 @@ 'iterate', 'last', 'locate', + 'longest_common_prefix', 'lstrip', 'make_decorator', 'map_except', @@ -133,9 +139,6 @@ -_marker = object() - - def chunked(iterable, n, strict=False): """Break *iterable* into lists of length *n*: @@ -410,44 +413,6 @@ return self._cacheindex -def collate(*iterables, **kwargs): - """Return a sorted merge of the items from each of several already-sorted - *iterables*. - - >>> list(collate('ACDZ', 'AZ', 'JKL')) - 'A', 'A', 'C', 'D', 'J', 'K', 'L', 'Z', 'Z' - - Works lazily, keeping only the next value from each iterable in memory. Use - :func:`collate` to, for example, perform a n-way mergesort of items that - don't fit in memory. - - If a *key* function is specified, the iterables will be sorted according - to its result: - - >>> key = lambda s: int(s) # Sort by numeric value, not by string - >>> list(collate('1', '10', '2', '11', key=key)) - '1', '2', '10', '11' - - - If the *iterables* are sorted in descending order, set *reverse* to - ``True``: - - >>> list(collate(5, 3, 1, 4, 2, 0, reverse=True)) - 5, 4, 3, 2, 1, 0 - - If the elements of the passed-in iterables are out of order, you might get - unexpected results. - - On Python 3.5+, this function is an alias for :func:`heapq.merge`. - - """ - warnings.warn( - "collate is no longer part of more_itertools, use heapq.merge", - DeprecationWarning, - ) - return merge(*iterables, **kwargs) - - def consumer(func): """Decorator that automatically advances a PEP-342-style "reverse iterator" to its first yield point so you don't have to call ``next()`` on it @@ -694,6 +659,7 @@ (0, 1), (0, 2), (1, 0), (1, 2), (2, 0), (2, 1) """ + # Algorithm: https://w.wiki/Qai def _full(A): while True: @@ -873,7 +839,9 @@ yield tuple(window) size = len(window) - if size < n: + if size == 0: + return + elif size < n: yield tuple(chain(window, repeat(fillvalue, n - size))) elif 0 < i < min(step, n): window += (fillvalue,) * i @@ -1335,7 +1303,7 @@ 0, 2, 4, 5, 6, 7, 8, 9 By default, the delimiting items are not included in the output. - The include them, set *keep_separator* to ``True``. + To include them, set *keep_separator* to ``True``. >>> list(split_at('abcdcba', lambda x: x == 'b', keep_separator=True)) 'a', 'b', 'c', 'd', 'c', 'b', 'a' @@ -1425,7 +1393,9 @@ if pred(item) and buf: yield buf if maxsplit == 1: - yield list(it) + buf = list(it) + if buf: + yield buf return buf = maxsplit -= 1 @@ -1646,45 +1616,6 @@ ) -class UnequalIterablesError(ValueError): - def __init__(self, details=None): - msg = 'Iterables have different lengths' - if details is not None: - msg += (': index 0 has length {}; index {} has length {}').format( - *details - ) - - super().__init__(msg) - - -def _zip_equal_generator(iterables): - for combo in zip_longest(*iterables, fillvalue=_marker): - for val in combo: - if val is _marker: - raise UnequalIterablesError() - yield combo - - -def _zip_equal(*iterables): - # Check whether the iterables are all the same size. - try: - first_size = len(iterables0) - for i, it in enumerate(iterables1:, 1): - size = len(it) - if size != first_size: - break - else: - # If we didn't break out, we can use the built-in zip. - return zip(*iterables) - - # If we did break out, there was a mismatch. - raise UnequalIterablesError(details=(first_size, i, size)) - # If any one of the iterables didn't have a length, start reading - # them until one runs out. - except TypeError: - return _zip_equal_generator(iterables) - - def zip_equal(*iterables): """``zip`` the input *iterables* together, but raise ``UnequalIterablesError`` if they aren't all the same length. @@ -1826,7 +1757,7 @@ of the zipped *iterable*.
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools/more.pyi -> _service:tar_scm:more-itertools-9.1.0.tar.gz/more_itertools/more.pyi
Changed
@@ -1,26 +1,25 @@ """Stubs for more_itertools.more""" +from __future__ import annotations +from types import TracebackType from typing import ( Any, Callable, Container, - Dict, + ContextManager, Generic, Hashable, Iterable, Iterator, - List, - Optional, + overload, Reversible, Sequence, Sized, - Tuple, - Union, + Type, TypeVar, type_check_only, ) -from types import TracebackType -from typing_extensions import ContextManager, Protocol, Type, overload +from typing_extensions import Protocol # Type and type variable definitions _T = TypeVar('_T') @@ -31,7 +30,7 @@ _W = TypeVar('_W') _T_co = TypeVar('_T_co', covariant=True) _GenFn = TypeVar('_GenFn', bound=Callable..., Iteratorobject) -_Raisable = UnionBaseException, 'TypeBaseException' +_Raisable = BaseException | TypeBaseException @type_check_only class _SizedIterable(Protocol_T_co, Sized, Iterable_T_co): ... @@ -39,23 +38,25 @@ @type_check_only class _SizedReversible(Protocol_T_co, Sized, Reversible_T_co): ... +@type_check_only +class _SupportsSlicing(Protocol_T_co): + def __getitem__(self, __k: slice) -> _T_co: ... + def chunked( - iterable: Iterable_T, n: Optionalint, strict: bool = ... -) -> IteratorList_T: ... + iterable: Iterable_T, n: int | None, strict: bool = ... +) -> Iteratorlist_T: ... @overload def first(iterable: Iterable_T) -> _T: ... @overload -def first(iterable: Iterable_T, default: _U) -> Union_T, _U: ... +def first(iterable: Iterable_T, default: _U) -> _T | _U: ... @overload def last(iterable: Iterable_T) -> _T: ... @overload -def last(iterable: Iterable_T, default: _U) -> Union_T, _U: ... +def last(iterable: Iterable_T, default: _U) -> _T | _U: ... @overload def nth_or_last(iterable: Iterable_T, n: int) -> _T: ... @overload -def nth_or_last( - iterable: Iterable_T, n: int, default: _U -) -> Union_T, _U: ... +def nth_or_last(iterable: Iterable_T, n: int, default: _U) -> _T | _U: ... class peekable(Generic_T, Iterator_T): def __init__(self, iterable: Iterable_T) -> None: ... @@ -64,15 +65,14 @@ @overload def peek(self) -> _T: ... @overload - def peek(self, default: _U) -> Union_T, _U: ... + def peek(self, default: _U) -> _T | _U: ... def prepend(self, *items: _T) -> None: ... def __next__(self) -> _T: ... @overload def __getitem__(self, index: int) -> _T: ... @overload - def __getitem__(self, index: slice) -> List_T: ... + def __getitem__(self, index: slice) -> list_T: ... -def collate(*iterables: Iterable_T, **kwargs: Any) -> Iterable_T: ... def consumer(func: _GenFn) -> _GenFn: ... def ilen(iterable: Iterableobject) -> int: ... def iterate(func: Callable_T, _T, start: _T) -> Iterator_T: ... @@ -81,42 +81,42 @@ ) -> Iterator_T: ... def one( iterable: Iterable_T, - too_short: Optional_Raisable = ..., - too_long: Optional_Raisable = ..., + too_short: _Raisable | None = ..., + too_long: _Raisable | None = ..., ) -> _T: ... def raise_(exception: _Raisable, *args: Any) -> None: ... def strictly_n( iterable: Iterable_T, n: int, - too_short: Optional_GenFn = ..., - too_long: Optional_GenFn = ..., -) -> List_T: ... + too_short: _GenFn | None = ..., + too_long: _GenFn | None = ..., +) -> list_T: ... def distinct_permutations( - iterable: Iterable_T, r: Optionalint = ... -) -> IteratorTuple_T, ...: ... + iterable: Iterable_T, r: int | None = ... +) -> Iteratortuple_T, ...: ... def intersperse( e: _U, iterable: Iterable_T, n: int = ... -) -> IteratorUnion_T, _U: ... -def unique_to_each(*iterables: Iterable_T) -> ListList_T: ... +) -> Iterator_T | _U: ... +def unique_to_each(*iterables: Iterable_T) -> listlist_T: ... @overload def windowed( seq: Iterable_T, n: int, *, step: int = ... -) -> IteratorTupleOptional_T, ...: ... +) -> Iteratortuple_T | None, ...: ... @overload def windowed( seq: Iterable_T, n: int, fillvalue: _U, step: int = ... -) -> IteratorTupleUnion_T, _U, ...: ... -def substrings(iterable: Iterable_T) -> IteratorTuple_T, ...: ... +) -> Iteratortuple_T | _U, ...: ... +def substrings(iterable: Iterable_T) -> Iteratortuple_T, ...: ... def substrings_indexes( seq: Sequence_T, reverse: bool = ... -) -> IteratorTupleSequence_T, int, int: ... +) -> IteratortupleSequence_T, int, int: ... class bucket(Generic_T, _U, Container_U): def __init__( self, iterable: Iterable_T, key: Callable_T, _U, - validator: OptionalCallableobject, object = ..., + validator: Callableobject, object | None = ..., ) -> None: ... def __contains__(self, value: object) -> bool: ... def __iter__(self) -> Iterator_U: ... @@ -124,117 +124,113 @@ def spy( iterable: Iterable_T, n: int = ... -) -> TupleList_T, Iterator_T: ... +) -> tuplelist_T, Iterator_T: ... def interleave(*iterables: Iterable_T) -> Iterator_T: ... def interleave_longest(*iterables: Iterable_T) -> Iterator_T: ... def interleave_evenly( - iterables: ListIterable_T, lengths: OptionalListint = ... + iterables: listIterable_T, lengths: listint | None = ... ) -> Iterator_T: ... def collapse( iterable: IterableAny, - base_type: Optionaltype = ..., - levels: Optionalint = ..., + base_type: type | None = ..., + levels: int | None = ..., ) -> IteratorAny: ... @overload def side_effect( func: Callable_T, object, iterable: Iterable_T, chunk_size: None = ..., - before: OptionalCallable, object = ..., - after: OptionalCallable, object = ..., + before: Callable, object | None = ..., + after: Callable, object | None = ..., ) -> Iterator_T: ... @overload def side_effect( - func: CallableList_T, object, + func: Callablelist_T, object, iterable: Iterable_T, chunk_size: int, - before: OptionalCallable, object = ..., - after: OptionalCallable, object = ..., + before: Callable, object | None = ..., + after: Callable, object | None = ..., ) -> Iterator_T: ... def sliced( - seq: Sequence_T, n: int, strict: bool = ... -) -> IteratorSequence_T: ... + seq: _SupportsSlicing_T, n: int, strict: bool = ... +) -> Iterator_T: ... def split_at( iterable: Iterable_T, pred: Callable_T, object, maxsplit: int = ..., keep_separator: bool = ...,
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools/recipes.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/more_itertools/recipes.py
Changed
@@ -7,33 +7,44 @@ .. 1 http://docs.python.org/library/itertools.html#recipes """ +import math +import operator import warnings + from collections import deque +from collections.abc import Sized +from functools import reduce from itertools import ( chain, combinations, + compress, count, cycle, groupby, islice, + product, repeat, starmap, tee, zip_longest, ) -import operator from random import randrange, sample, choice +from sys import hexversion __all__ = 'all_equal', + 'batched', 'before_and_after', 'consume', 'convolve', 'dotproduct', 'first_true', + 'factor', 'flatten', 'grouper', 'iter_except', + 'iter_index', + 'matmul', 'ncycles', 'nth', 'nth_combination', @@ -41,6 +52,7 @@ 'pad_none', 'pairwise', 'partition', + 'polynomial_from_roots', 'powerset', 'prepend', 'quantify', @@ -50,15 +62,20 @@ 'random_product', 'repeatfunc', 'roundrobin', + 'sieve', 'sliding_window', + 'subslices', 'tabulate', 'tail', 'take', + 'transpose', 'triplewise', 'unique_everseen', 'unique_justseen', +_marker = object() + def take(n, iterable): """Return first *n* items of the iterable as a list. @@ -102,7 +119,14 @@ 'E', 'F', 'G' """ - return iter(deque(iterable, maxlen=n)) + # If the given iterable has a length, then we can use islice to get its + # final elements. Note that if the iterable is not actually Iterable, + # either islice or deque will throw a TypeError. This is why we don't + # check if it is Iterable. + if isinstance(iterable, Sized): + yield from islice(iterable, max(0, len(iterable) - n), None) + else: + yield from iter(deque(iterable, maxlen=n)) def consume(iterator, n=None): @@ -284,20 +308,83 @@ pairwise.__doc__ = _pairwise.__doc__ -def grouper(iterable, n, fillvalue=None): - """Collect data into fixed-length chunks or blocks. +class UnequalIterablesError(ValueError): + def __init__(self, details=None): + msg = 'Iterables have different lengths' + if details is not None: + msg += (': index 0 has length {}; index {} has length {}').format( + *details + ) + + super().__init__(msg) + + +def _zip_equal_generator(iterables): + for combo in zip_longest(*iterables, fillvalue=_marker): + for val in combo: + if val is _marker: + raise UnequalIterablesError() + yield combo + + +def _zip_equal(*iterables): + # Check whether the iterables are all the same size. + try: + first_size = len(iterables0) + for i, it in enumerate(iterables1:, 1): + size = len(it) + if size != first_size: + break + else: + # If we didn't break out, we can use the built-in zip. + return zip(*iterables) + + # If we did break out, there was a mismatch. + raise UnequalIterablesError(details=(first_size, i, size)) + # If any one of the iterables didn't have a length, start reading + # them until one runs out. + except TypeError: + return _zip_equal_generator(iterables) + + +def grouper(iterable, n, incomplete='fill', fillvalue=None): + """Group elements from *iterable* into fixed-length groups of length *n*. + + >>> list(grouper('ABCDEF', 3)) + ('A', 'B', 'C'), ('D', 'E', 'F') + + The keyword arguments *incomplete* and *fillvalue* control what happens for + iterables whose length is not a multiple of *n*. + + When *incomplete* is `'fill'`, the last group will contain instances of + *fillvalue*. - >>> list(grouper('ABCDEFG', 3, 'x')) + >>> list(grouper('ABCDEFG', 3, incomplete='fill', fillvalue='x')) ('A', 'B', 'C'), ('D', 'E', 'F'), ('G', 'x', 'x') + When *incomplete* is `'ignore'`, the last group will not be emitted. + + >>> list(grouper('ABCDEFG', 3, incomplete='ignore', fillvalue='x')) + ('A', 'B', 'C'), ('D', 'E', 'F') + + When *incomplete* is `'strict'`, a subclass of `ValueError` will be raised. + + >>> it = grouper('ABCDEFG', 3, incomplete='strict') + >>> list(it) # doctest: +IGNORE_EXCEPTION_DETAIL + Traceback (most recent call last): + ... + UnequalIterablesError + """ - if isinstance(iterable, int): - warnings.warn( - "grouper expects iterable as first parameter", DeprecationWarning - ) - n, iterable = iterable, n args = iter(iterable) * n - return zip_longest(fillvalue=fillvalue, *args) + if incomplete == 'fill': + return zip_longest(*args, fillvalue=fillvalue) + if incomplete == 'strict': + return _zip_equal(*args) + if incomplete == 'ignore': + return zip(*args) + else: + raise ValueError('Expected fill, strict, or ignore') def roundrobin(*iterables): @@ -658,11 +745,12 @@ transition.append(elem) return - def remainder_iterator(): - yield from transition - yield from it + # Note: this is different from itertools recipes to allow nesting + # before_and_after remainders into before_and_after again. See tests + # for an example. + remainder_iterator = chain(transition, it) - return true_iterator(), remainder_iterator() + return true_iterator(), remainder_iterator
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/more_itertools/recipes.pyi -> _service:tar_scm:more-itertools-9.1.0.tar.gz/more_itertools/recipes.pyi
Changed
@@ -1,112 +1,119 @@ """Stubs for more_itertools.recipes""" +from __future__ import annotations + from typing import ( Any, Callable, Iterable, Iterator, - List, - Optional, - Tuple, + overload, + Sequence, + Type, TypeVar, - Union, ) -from typing_extensions import overload, Type # Type and type variable definitions _T = TypeVar('_T') _U = TypeVar('_U') -def take(n: int, iterable: Iterable_T) -> List_T: ... +def take(n: int, iterable: Iterable_T) -> list_T: ... def tabulate( function: Callableint, _T, start: int = ... ) -> Iterator_T: ... def tail(n: int, iterable: Iterable_T) -> Iterator_T: ... -def consume(iterator: Iterableobject, n: Optionalint = ...) -> None: ... +def consume(iterator: Iterableobject, n: int | None = ...) -> None: ... @overload -def nth(iterable: Iterable_T, n: int) -> Optional_T: ... +def nth(iterable: Iterable_T, n: int) -> _T | None: ... @overload -def nth(iterable: Iterable_T, n: int, default: _U) -> Union_T, _U: ... +def nth(iterable: Iterable_T, n: int, default: _U) -> _T | _U: ... def all_equal(iterable: Iterableobject) -> bool: ... def quantify( iterable: Iterable_T, pred: Callable_T, bool = ... ) -> int: ... -def pad_none(iterable: Iterable_T) -> IteratorOptional_T: ... -def padnone(iterable: Iterable_T) -> IteratorOptional_T: ... +def pad_none(iterable: Iterable_T) -> Iterator_T | None: ... +def padnone(iterable: Iterable_T) -> Iterator_T | None: ... def ncycles(iterable: Iterable_T, n: int) -> Iterator_T: ... def dotproduct(vec1: Iterableobject, vec2: Iterableobject) -> object: ... def flatten(listOfLists: IterableIterable_T) -> Iterator_T: ... def repeatfunc( - func: Callable..., _U, times: Optionalint = ..., *args: Any + func: Callable..., _U, times: int | None = ..., *args: Any ) -> Iterator_U: ... -def pairwise(iterable: Iterable_T) -> IteratorTuple_T, _T: ... -@overload -def grouper( - iterable: Iterable_T, n: int -) -> IteratorTupleOptional_T, ...: ... -@overload +def pairwise(iterable: Iterable_T) -> Iteratortuple_T, _T: ... def grouper( - iterable: Iterable_T, n: int, fillvalue: _U -) -> IteratorTupleUnion_T, _U, ...: ... -@overload -def grouper( # Deprecated interface - iterable: int, n: Iterable_T -) -> IteratorTupleOptional_T, ...: ... -@overload -def grouper( # Deprecated interface - iterable: int, n: Iterable_T, fillvalue: _U -) -> IteratorTupleUnion_T, _U, ...: ... + iterable: Iterable_T, + n: int, + incomplete: str = ..., + fillvalue: _U = ..., +) -> Iteratortuple_T | _U, ...: ... def roundrobin(*iterables: Iterable_T) -> Iterator_T: ... def partition( - pred: OptionalCallable_T, object, iterable: Iterable_T -) -> TupleIterator_T, Iterator_T: ... -def powerset(iterable: Iterable_T) -> IteratorTuple_T, ...: ... + pred: Callable_T, object | None, iterable: Iterable_T +) -> tupleIterator_T, Iterator_T: ... +def powerset(iterable: Iterable_T) -> Iteratortuple_T, ...: ... def unique_everseen( - iterable: Iterable_T, key: OptionalCallable_T, _U = ... + iterable: Iterable_T, key: Callable_T, _U | None = ... ) -> Iterator_T: ... def unique_justseen( - iterable: Iterable_T, key: OptionalCallable_T, object = ... + iterable: Iterable_T, key: Callable_T, object | None = ... ) -> Iterator_T: ... @overload def iter_except( func: Callable, _T, - exception: UnionTypeBaseException, TupleTypeBaseException, ..., + exception: TypeBaseException | tupleTypeBaseException, ..., first: None = ..., ) -> Iterator_T: ... @overload def iter_except( func: Callable, _T, - exception: UnionTypeBaseException, TupleTypeBaseException, ..., + exception: TypeBaseException | tupleTypeBaseException, ..., first: Callable, _U, -) -> IteratorUnion_T, _U: ... +) -> Iterator_T | _U: ... @overload def first_true( - iterable: Iterable_T, *, pred: OptionalCallable_T, object = ... -) -> Optional_T: ... + iterable: Iterable_T, *, pred: Callable_T, object | None = ... +) -> _T | None: ... @overload def first_true( iterable: Iterable_T, default: _U, - pred: OptionalCallable_T, object = ..., -) -> Union_T, _U: ... + pred: Callable_T, object | None = ..., +) -> _T | _U: ... def random_product( *args: Iterable_T, repeat: int = ... -) -> Tuple_T, ...: ... +) -> tuple_T, ...: ... def random_permutation( - iterable: Iterable_T, r: Optionalint = ... -) -> Tuple_T, ...: ... -def random_combination(iterable: Iterable_T, r: int) -> Tuple_T, ...: ... + iterable: Iterable_T, r: int | None = ... +) -> tuple_T, ...: ... +def random_combination(iterable: Iterable_T, r: int) -> tuple_T, ...: ... def random_combination_with_replacement( iterable: Iterable_T, r: int -) -> Tuple_T, ...: ... +) -> tuple_T, ...: ... def nth_combination( iterable: Iterable_T, r: int, index: int -) -> Tuple_T, ...: ... -def prepend(value: _T, iterator: Iterable_U) -> IteratorUnion_T, _U: ... +) -> tuple_T, ...: ... +def prepend(value: _T, iterator: Iterable_U) -> Iterator_T | _U: ... def convolve(signal: Iterable_T, kernel: Iterable_T) -> Iterator_T: ... def before_and_after( predicate: Callable_T, bool, it: Iterable_T -) -> TupleIterator_T, Iterator_T: ... -def triplewise(iterable: Iterable_T) -> IteratorTuple_T, _T, _T: ... +) -> tupleIterator_T, Iterator_T: ... +def triplewise(iterable: Iterable_T) -> Iteratortuple_T, _T, _T: ... def sliding_window( iterable: Iterable_T, n: int -) -> IteratorTuple_T, ...: ... +) -> Iteratortuple_T, ...: ... +def subslices(iterable: Iterable_T) -> Iteratorlist_T: ... +def polynomial_from_roots(roots: Sequenceint) -> listint: ... +def iter_index( + iterable: Iterableobject, + value: Any, + start: int | None = ..., +) -> Iteratorint: ... +def sieve(n: int) -> Iteratorint: ... +def batched( + iterable: Iterable_T, + n: int, +) -> Iteratorlist_T: ... +def transpose( + it: IterableIterable_T, +) -> tupleIterator_T, ...: ... +def matmul(m1: Sequence_T, m2: Sequence_T) -> Iteratorlist_T: ... +def factor(n: int) -> Iteratorint: ...
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/pyproject.toml -> _service:tar_scm:more-itertools-9.1.0.tar.gz/pyproject.toml
Changed
@@ -1,4 +1,48 @@ +build-system +requires = "flit_core >=3.2,<4" +build-backend = "flit_core.buildapi" + +project +name = "more-itertools" +authors = {name = "Erik Rose", email = "erikrose@grinchcentral.com"} +readme = "README.rst" +requires-python = ">=3.7" +license = {file = "LICENSE"} +keywords = + "itertools", + "iterator", + "iteration", + "filter", + "peek", + "peekable", + "chunk", + "chunked", + +classifiers = + "Development Status :: 5 - Production/Stable", + "Intended Audience :: Developers", + "Natural Language :: English", + "License :: OSI Approved :: MIT License", + "Programming Language :: Python :: 3", + "Programming Language :: Python :: 3.7", + "Programming Language :: Python :: 3.8", + "Programming Language :: Python :: 3.9", + "Programming Language :: Python :: 3.10", + "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3 :: Only", + "Programming Language :: Python :: Implementation :: CPython", + "Programming Language :: Python :: Implementation :: PyPy", + "Topic :: Software Development :: Libraries", + +dynamic = "version", "description" + +project.urls +Homepage = "https://github.com/more-itertools/more-itertools" + +tool.flit.module +name = "more_itertools" + tool.black line-length = 79 -target-version = 'py35' +target-version = 'py37' skip-string-normalization = true
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/setup.cfg -> _service:tar_scm:more-itertools-9.1.0.tar.gz/setup.cfg
Changed
@@ -1,5 +1,5 @@ bumpversion -current_version = 8.12.0 +current_version = 9.1.0 commit = True tag = False files = more_itertools/__init__.py
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/setup.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/setup.py
Changed
@@ -1,66 +1,3 @@ -from re import sub - from setuptools import setup -from more_itertools import __version__ - - -def get_long_description(): - # Fix display issues on PyPI caused by RST markup - readme = open('README.rst').read() - - version_lines = - with open('docs/versions.rst') as infile: - next(infile) - for line in infile: - line = line.rstrip().replace('.. automodule:: more_itertools', '') - if line == '5.0.0': - break - version_lines.append(line) - version_history = '\n'.join(version_lines) - version_history = sub(r':func:`(a-zA-Z0-9._+)`', r'\1', version_history) - - ret = readme + '\n\n' + version_history - return ret - - -setup( - name='more-itertools', - version=__version__, - description='More routines for operating on iterables, beyond itertools', - long_description=get_long_description(), - long_description_content_type='text/x-rst', - author='Erik Rose', - author_email='erikrose@grinchcentral.com', - license='MIT', - packages='more_itertools', - package_data={'more_itertools': 'py.typed', '*.pyi'}, - python_requires='>=3.5', - url='https://github.com/more-itertools/more-itertools', - classifiers= - 'Development Status :: 5 - Production/Stable', - 'Intended Audience :: Developers', - 'Natural Language :: English', - 'License :: OSI Approved :: MIT License', - 'Programming Language :: Python :: 3', - 'Programming Language :: Python :: 3.6', - 'Programming Language :: Python :: 3.7', - 'Programming Language :: Python :: 3.8', - 'Programming Language :: Python :: 3.9', - 'Programming Language :: Python :: 3 :: Only', - 'Programming Language :: Python :: Implementation :: CPython', - 'Programming Language :: Python :: Implementation :: PyPy', - 'Topic :: Software Development :: Libraries', - , - keywords= - 'itertools', - 'iterator', - 'iteration', - 'filter', - 'peek', - 'peekable', - 'collate', - 'chunk', - 'chunked', - , -) +setup()
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/tests/test_more.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/tests/test_more.py
Changed
@@ -7,7 +7,6 @@ from doctest import DocTestSuite from fractions import Fraction from functools import partial, reduce -from heapq import merge from io import StringIO from itertools import ( accumulate, @@ -23,10 +22,11 @@ ) from operator import add, mul, itemgetter from pickle import loads, dumps +from platform import python_implementation from random import seed, Random from statistics import mean from string import ascii_letters -from sys import version_info +from sys import version_info, getsizeof from time import sleep from traceback import format_exc from unittest import skipIf, TestCase @@ -40,51 +40,6 @@ return tests -class CollateTests(TestCase): - """Unit tests for ``collate()``""" - - # Also accidentally tests peekable, though that could use its own tests - - def test_default(self): - """Test with the default `key` function.""" - iterables = range(4), range(7), range(3, 6) - self.assertEqual( - sorted(reduce(list.__add__, list(it) for it in iterables)), - list(mi.collate(*iterables)), - ) - - def test_key(self): - """Test using a custom `key` function.""" - iterables = range(5, 0, -1), range(4, 0, -1) - actual = sorted( - reduce(list.__add__, list(it) for it in iterables), reverse=True - ) - expected = list(mi.collate(*iterables, key=lambda x: -x)) - self.assertEqual(actual, expected) - - def test_empty(self): - """Be nice if passed an empty list of iterables.""" - self.assertEqual(, list(mi.collate())) - - def test_one(self): - """Work when only 1 iterable is passed.""" - self.assertEqual(0, 1, list(mi.collate(range(2)))) - - def test_reverse(self): - """Test the `reverse` kwarg.""" - iterables = range(4, 0, -1), range(7, 0, -1), range(3, 6, -1) - - actual = sorted( - reduce(list.__add__, list(it) for it in iterables), reverse=True - ) - expected = list(mi.collate(*iterables, reverse=True)) - self.assertEqual(actual, expected) - - def test_alias(self): - self.assertNotEqual(merge.__doc__, mi.collate.__doc__) - self.assertNotEqual(partial.__doc__, mi.collate.__doc__) - - class ChunkedTests(TestCase): """Tests for ``chunked()``""" @@ -288,11 +243,6 @@ class PeekableTests(PeekableMixinTests, TestCase): - """Tests for ``peekable()`` behavior not incidentally covered by testing - ``collate()`` - - """ - cls = mi.peekable def test_indexing(self): @@ -782,64 +732,55 @@ class WindowedTests(TestCase): - """Tests for ``windowed()``""" - def test_basic(self): - actual = list(mi.windowed(1, 2, 3, 4, 5, 3)) - expected = (1, 2, 3), (2, 3, 4), (3, 4, 5) - self.assertEqual(actual, expected) - - def test_large_size(self): - """ - When the window size is larger than the iterable, and no fill value is - given,``None`` should be filled in. - """ - actual = list(mi.windowed(1, 2, 3, 4, 5, 6)) - expected = (1, 2, 3, 4, 5, None) - self.assertEqual(actual, expected) - - def test_fillvalue(self): - """ - When sizes don't match evenly, the given fill value should be used. - """ iterable = 1, 2, 3, 4, 5 - for n, kwargs, expected in - (6, {}, (1, 2, 3, 4, 5, '!')), # n > len(iterable) - (3, {'step': 3}, (1, 2, 3), (4, 5, '!')), # using ``step`` - : - actual = list(mi.windowed(iterable, n, fillvalue='!', **kwargs)) - self.assertEqual(actual, expected) + for n, expected in ( + (6, (1, 2, 3, 4, 5, None)), + (5, (1, 2, 3, 4, 5)), + (4, (1, 2, 3, 4), (2, 3, 4, 5)), + (3, (1, 2, 3), (2, 3, 4), (3, 4, 5)), + (2, (1, 2), (2, 3), (3, 4), (4, 5)), + (1, (1,), (2,), (3,), (4,), (5,)), + (0, ()), + ): + with self.subTest(n=n): + actual = list(mi.windowed(iterable, n)) + self.assertEqual(actual, expected) - def test_zero(self): - """When the window size is zero, an empty tuple should be emitted.""" - actual = list(mi.windowed(1, 2, 3, 4, 5, 0)) - expected = tuple() + def test_fillvalue(self): + actual = list(mi.windowed(1, 2, 3, 4, 5, 6, fillvalue='!')) + expected = (1, 2, 3, 4, 5, '!') self.assertEqual(actual, expected) - def test_negative(self): - """When the window size is negative, ValueError should be raised.""" - with self.assertRaises(ValueError): - list(mi.windowed(1, 2, 3, 4, 5, -1)) - def test_step(self): - """The window should advance by the number of steps provided""" iterable = 1, 2, 3, 4, 5, 6, 7 for n, step, expected in (3, 2, (1, 2, 3), (3, 4, 5), (5, 6, 7)), # n > step (3, 3, (1, 2, 3), (4, 5, 6), (7, None, None)), # n == step - (3, 4, (1, 2, 3), (5, 6, 7)), # line up nicely + (3, 4, (1, 2, 3), (5, 6, 7)), # lines up nicely (3, 5, (1, 2, 3), (6, 7, None)), # off by one (3, 6, (1, 2, 3), (7, None, None)), # off by two (3, 7, (1, 2, 3)), # step past the end (7, 8, (1, 2, 3, 4, 5, 6, 7)), # step > len(iterable) : - actual = list(mi.windowed(iterable, n, step=step)) - self.assertEqual(actual, expected) + with self.subTest(n=n, step=step): + actual = list(mi.windowed(iterable, n, step=step)) + self.assertEqual(actual, expected) + def test_invalid_step(self): # Step must be greater than or equal to 1 with self.assertRaises(ValueError): - list(mi.windowed(iterable, 3, step=0)) + list(mi.windowed(1, 2, 3, 4, 5, 3, step=0)) + + def test_fillvalue_step(self): + actual = list(mi.windowed(1, 2, 3, 4, 5, 3, fillvalue='!', step=3)) + expected = (1, 2, 3), (4, 5, '!') + self.assertEqual(actual, expected) + + def test_negative(self): + with self.assertRaises(ValueError): + list(mi.windowed(1, 2, 3, 4, 5, -1)) class SubstringsTests(TestCase): @@ -1507,6 +1448,10 @@ ('a,b,c,d', lambda c: c != ',', 2), 'a', ',', 'b', ',', 'c', ',', 'd', ), + ( + (1, lambda x: x == 1, 1), + 1, + ), : actual = list(mi.split_after(*args)) self.assertEqual(actual, expected) @@ -3217,8 +3162,8 @@ class IsliceExtendedTests(TestCase): def test_all(self): iterable = '0', '1', '2', '3', '4', '5' - indexes = list(range(-4, len(iterable) + 4)) + None - steps = 1, 2, 3, 4, -1, -2, -3, 4 + indexes = *range(-4, 10), None + steps = 1, 2, 3, 4, -1, -2, -3, -4 for slice_args in product(indexes, indexes, steps):
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/tests/test_recipes.py -> _service:tar_scm:more-itertools-9.1.0.tar.gz/tests/test_recipes.py
Changed
@@ -1,7 +1,7 @@ -import warnings - from doctest import DocTestSuite +from functools import reduce from itertools import combinations, count, permutations +from operator import mul from math import factorial from unittest import TestCase @@ -59,21 +59,29 @@ class TailTests(TestCase): """Tests for ``tail()``""" - def test_greater(self): - """Length of iterable is greater than requested tail""" - self.assertEqual(list(mi.tail(3, 'ABCDEFG')), 'E', 'F', 'G') + def test_iterator_greater(self): + """Length of iterator is greater than requested tail""" + self.assertEqual(list(mi.tail(3, iter('ABCDEFG'))), list('EFG')) - def test_equal(self): - """Length of iterable is equal to the requested tail""" - self.assertEqual( - list(mi.tail(7, 'ABCDEFG')), 'A', 'B', 'C', 'D', 'E', 'F', 'G' - ) + def test_iterator_equal(self): + """Length of iterator is equal to the requested tail""" + self.assertEqual(list(mi.tail(7, iter('ABCDEFG'))), list('ABCDEFG')) - def test_less(self): - """Length of iterable is less than requested tail""" - self.assertEqual( - list(mi.tail(8, 'ABCDEFG')), 'A', 'B', 'C', 'D', 'E', 'F', 'G' - ) + def test_iterator_less(self): + """Length of iterator is less than requested tail""" + self.assertEqual(list(mi.tail(8, iter('ABCDEFG'))), list('ABCDEFG')) + + def test_sized_greater(self): + """Length of sized iterable is greater than requested tail""" + self.assertEqual(list(mi.tail(3, 'ABCDEFG')), list('EFG')) + + def test_sized_equal(self): + """Length of sized iterable is less than requested tail""" + self.assertEqual(list(mi.tail(7, 'ABCDEFG')), list('ABCDEFG')) + + def test_sized_less(self): + """Length of sized iterable is less than requested tail""" + self.assertEqual(list(mi.tail(8, 'ABCDEFG')), list('ABCDEFG')) class ConsumeTests(TestCase): @@ -259,44 +267,77 @@ class GrouperTests(TestCase): - """Tests for ``grouper()``""" - - def test_even(self): - """Test when group size divides evenly into the length of - the iterable. - - """ - self.assertEqual( - list(mi.grouper('ABCDEF', 3)), ('A', 'B', 'C'), ('D', 'E', 'F') - ) + def test_basic(self): + seq = 'ABCDEF' + for n, expected in + (3, ('A', 'B', 'C'), ('D', 'E', 'F')), + (4, ('A', 'B', 'C', 'D'), ('E', 'F', None, None)), + (5, ('A', 'B', 'C', 'D', 'E'), ('F', None, None, None, None)), + (6, ('A', 'B', 'C', 'D', 'E', 'F')), + (7, ('A', 'B', 'C', 'D', 'E', 'F', None)), + : + with self.subTest(n=n): + actual = list(mi.grouper(iter(seq), n)) + self.assertEqual(actual, expected) - def test_odd(self): - """Test when group size does not divide evenly into the length of the - iterable. + def test_fill(self): + seq = 'ABCDEF' + fillvalue = 'x' + for n, expected in + (1, 'A', 'B', 'C', 'D', 'E', 'F'), + (2, 'AB', 'CD', 'EF'), + (3, 'ABC', 'DEF'), + (4, 'ABCD', 'EFxx'), + (5, 'ABCDE', 'Fxxxx'), + (6, 'ABCDEF'), + (7, 'ABCDEFx'), + : + with self.subTest(n=n): + it = mi.grouper( + iter(seq), n, incomplete='fill', fillvalue=fillvalue + ) + actual = ''.join(x) for x in it + self.assertEqual(actual, expected) - """ - self.assertEqual( - list(mi.grouper('ABCDE', 3)), ('A', 'B', 'C'), ('D', 'E', None) - ) + def test_ignore(self): + seq = 'ABCDEF' + for n, expected in + (1, 'A', 'B', 'C', 'D', 'E', 'F'), + (2, 'AB', 'CD', 'EF'), + (3, 'ABC', 'DEF'), + (4, 'ABCD'), + (5, 'ABCDE'), + (6, 'ABCDEF'), + (7, ), + : + with self.subTest(n=n): + it = mi.grouper(iter(seq), n, incomplete='ignore') + actual = ''.join(x) for x in it + self.assertEqual(actual, expected) - def test_fill_value(self): - """Test that the fill value is used to pad the final group""" - self.assertEqual( - list(mi.grouper('ABCDE', 3, 'x')), - ('A', 'B', 'C'), ('D', 'E', 'x'), - ) + def test_strict(self): + seq = 'ABCDEF' + for n, expected in + (1, 'A', 'B', 'C', 'D', 'E', 'F'), + (2, 'AB', 'CD', 'EF'), + (3, 'ABC', 'DEF'), + (6, 'ABCDEF'), + : + with self.subTest(n=n): + it = mi.grouper(iter(seq), n, incomplete='strict') + actual = ''.join(x) for x in it + self.assertEqual(actual, expected) - def test_legacy_order(self): - """Historically, grouper expected the n as the first parameter""" - with warnings.catch_warnings(record=True) as caught: - warnings.simplefilter('always') - self.assertEqual( - list(mi.grouper(3, 'ABCDEF')), - ('A', 'B', 'C'), ('D', 'E', 'F'), - ) + def test_strict_fails(self): + seq = 'ABCDEF' + for n in 4, 5, 7: + with self.subTest(n=n): + with self.assertRaises(ValueError): + list(mi.grouper(iter(seq), n, incomplete='strict')) - (warning,) = caught - assert warning.category == DeprecationWarning + def test_invalid_incomplete(self): + with self.assertRaises(ValueError): + list(mi.grouper('ABCD', 3, incomplete='bogus')) class RoundrobinTests(TestCase): @@ -732,6 +773,39 @@ self.assertEqual(list(before), 1, True) self.assertEqual(list(after), 0, False) + @staticmethod + def _group_events(events): + events = iter(events) + + while True: + try: + operation = next(events) + except StopIteration: + break + assert operation in "SUM", "MULTIPLY" + + # Here, the remainder `events` is passed into `before_and_after` + # again, which would be problematic if the remainder is a + # generator function (as in Python 3.10 itertools recipes), since + # that creates recursion. `itertools.chain` solves this problem. + numbers, events = mi.before_and_after( + lambda e: isinstance(e, int), events + ) + + yield (operation, numbers) + + def test_nested_remainder(self): + events = "SUM", 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 * 1000 + events += "MULTIPLY", 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 * 1000 + + for operation, numbers in self._group_events(events): + if operation == "SUM": + res = sum(numbers) + self.assertEqual(res, 55) + elif operation == "MULTIPLY": + res = reduce(lambda a, b: a * b, numbers) + self.assertEqual(res, 3628800)
View file
_service:tar_scm:more-itertools-8.12.0.tar.gz/tox.ini -> _service:tar_scm:more-itertools-9.1.0.tar.gz/tox.ini
Changed
@@ -1,5 +1,6 @@ tox envlist = py{36,37,38,39} +isolated_build = True testenv commands = {envpython} -m unittest -v {posargs}
Locations
Projects
Search
Status Monitor
Help
Open Build Service
OBS Manuals
API Documentation
OBS Portal
Reporting a Bug
Contact
Mailing List
Forums
Chat (IRC)
Twitter
Open Build Service (OBS)
is an
openSUSE project
.
浙ICP备2022010568号-2