Repository: sympy/sympy
Pull request: iterables - fixes issue 21863 and now multiset_permutations can handle []
<!-- Your title above should be a short description of what
was changed. Do not include the issue number in the title. -->

#### References to other Issues or PRs
<!-- If this pull request fixes an issue, write "Fixes #NNNN" in that exact
format, e.g. "Fixes #1234" (see
https://tinyurl.com/auto-closing for more information). Also, please
write a comment on that issue linking back to this pull request once it is
open. -->


#### Brief description of what is fixed or changed
Fixes #21863 and now multiset_permutations can handle null/empty sets and also added regression tests in test_iterables.py

#### Other comments


#### Release Notes

<!-- Write the release notes for this release below between the BEGIN and END
statements. The basic format is a bulleted list with the name of the subpackage
and the release note for this PR. For example:

* solvers
  * Added a new solver for logarithmic equations.

* functions
  * Fixed a bug with log of integers.

or if no release note(s) should be included use:

NO ENTRY

See https://github.com/sympy/sympy/wiki/Writing-Release-Notes for more
information on how to write release notes. The bot will check your release
notes automatically to see if they are formatted correctly. -->

<!-- BEGIN RELEASE NOTES -->
* utilities
    * Fixed bug in iterables.py and now multiset_permutations can handle []
<!-- END RELEASE NOTES -->


Problem statement:
multiset_permutations needs to handle []
```diff
diff --git a/sympy/utilities/iterables.py b/sympy/utilities/iterables.py
index 83fc2f48d2..0a91615dde 100644
--- a/sympy/utilities/iterables.py
+++ b/sympy/utilities/iterables.py
@@ -1419,7 +1419,7 @@ def multiset_permutations(m, size=None, g=None):
     do = [gi for gi in g if gi[1] > 0]
     SUM = sum([gi[1] for gi in do])
     if not do or size is not None and (size > SUM or size < 1):
-        if size < 1:
+        if not do and size is None or size < 1:
             yield []
         return
     elif size == 1:
diff --git a/sympy/utilities/tests/test_iterables.py b/sympy/utilities/tests/test_iterables.py
index 221b03f618..b405ac37f5 100644
--- a/sympy/utilities/tests/test_iterables.py
+++ b/sympy/utilities/tests/test_iterables.py
@@ -423,6 +423,9 @@ def test_multiset_permutations():
         [0, 1], [0, 2], [1, 0], [1, 2], [2, 0], [2, 1]]
     assert len(list(multiset_permutations('a', 0))) == 1
     assert len(list(multiset_permutations('a', 3))) == 0
+    for nul in ([], {}, ''):
+        assert list(multiset_permutations(nul)) == [[]], list(multiset_permutations(nul))
+        assert list(multiset_permutations(nul, 1)) == []
 
     def test():
         for i in range(1, 7):
```

Hints from issue discussion:

Commit message: fixed issue 21863

Patch to review:
diff --git a/sympy/utilities/iterables.py b/sympy/utilities/iterables.py
index 83fc2f48d2e9..0a91615ddedd 100644
--- a/sympy/utilities/iterables.py
+++ b/sympy/utilities/iterables.py
@@ -1419,7 +1419,7 @@ def multiset_permutations(m, size=None, g=None):
     do = [gi for gi in g if gi[1] > 0]
     SUM = sum([gi[1] for gi in do])
     if not do or size is not None and (size > SUM or size < 1):
-        if size < 1:
+        if not do and size is None or size < 1:
             yield []
         return
     elif size == 1:
diff --git a/sympy/utilities/tests/test_iterables.py b/sympy/utilities/tests/test_iterables.py
index 221b03f61883..b405ac37f5ad 100644
--- a/sympy/utilities/tests/test_iterables.py
+++ b/sympy/utilities/tests/test_iterables.py
@@ -423,6 +423,9 @@ def test_multiset_permutations():
         [0, 1], [0, 2], [1, 0], [1, 2], [2, 0], [2, 1]]
     assert len(list(multiset_permutations('a', 0))) == 1
     assert len(list(multiset_permutations('a', 3))) == 0
+    for nul in ([], {}, ''):
+        assert list(multiset_permutations(nul)) == [[]], list(multiset_permutations(nul))
+        assert list(multiset_permutations(nul, 1)) == []
 
     def test():
         for i in range(1, 7):


Code review comments:
diff_hunk: @@ -1419,7 +1419,7 @@ def multiset_permutations(m, size=None, g=None):
     do = [gi for gi in g if gi[1] > 0]
     SUM = sum([gi[1] for gi in do])
     if not do or size is not None and (size > SUM or size < 1):
-        if size < 1:
+        if not do and size is None or size < 1:
path: sympy/utilities/iterables.py
text: @user1:
```suggestion
        if not do and size is None or size == 0:
```

diff_hunk: @@ -423,6 +423,9 @@ def test_multiset_permutations():
         [0, 1], [0, 2], [1, 0], [1, 2], [2, 0], [2, 1]]
     assert len(list(multiset_permutations('a', 0))) == 1
     assert len(list(multiset_permutations('a', 3))) == 0
+    for nul in ([], {}, ''):
+        assert list(multiset_permutations(nul)) == [[]], list(multiset_permutations(nul))
+        assert list(multiset_permutations(nul, 1)) == []
path: sympy/utilities/tests/test_iterables.py
text: @user1:
```suggestion
        assert list(multiset_permutations(nul)) == [[]]
    assert list(multiset_permutations(nul, 0)) == [[]]
    # impossible requests give no result
    assert list(multiset_permutations(nul, 1)) == []
    assert list(multiset_permutations(nul, -1)) == []
```