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

Idea: auto-resizing infinite iterables for variable initialization #13

Open
Technologicat opened this issue Aug 8, 2019 · 0 comments
Open
Labels
discussion Thinking it over - comments welcome! enhancement New feature or request
Milestone

Comments

@Technologicat
Copy link
Owner

This would be occasionally useful:

from itertools import repeat
from unpythonic.syntax import macros, autotrunc  # DOES NOT EXIST YET

with autotrunc:
    a, b, c = repeat(None)

Concise, and we don't have to manually repeat the unimportant detail of how many names are on the LHS, since this information is already lexically available (just count from the AST).

The equivalent pure Python is:

from itertools import repeat

a, b, c = repeat(None, 3)

The solution must be a block macro, because it must have the assignment LHS in its context in order to count the names there. We can't do anything about this in the function call, or even as an expr macro for the RHS - at that point it's not yet known where the output is going to be sent.

However, is this so useful after all? We need to be careful with edge cases such as:

a, *b, c = repeat(42)  # error, an infinite iterable has no last item
*a, b, c = repeat(42)  # error, likewise
a, b, *c = repeat(42)  # ok, a = 42, b = 42, c = repeat(42)

In the first example, for the specific case of repeat we could define it to extract one 42 and assign it to c, but that doesn't generalize. It's better to refuse the temptation to guess.

Unpacking the start of an arbitrary infinite iterable can be trivially defined by delegating to unpythonic.it.unpack. The third example could expand to:

from unpythonic import unpack
a, b, *c = unpack(2, repeat(42))

(Since an assignment always appears in a block of statements, we can always prepend the import.)

Another case to consider are finite inputs. For example, if len(seq) == 5:

a, *b, c = seq

Python itself already knows to do the right thing here. How would autotrunc avoid putting its nose where it doesn't belong?

@Technologicat Technologicat added enhancement New feature or request question Further information is requested labels Aug 8, 2019
@Technologicat Technologicat added this to the far-future milestone Aug 8, 2019
@Technologicat Technologicat added discussion Thinking it over - comments welcome! and removed question Further information is requested labels Aug 8, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
discussion Thinking it over - comments welcome! enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

1 participant