The following syntax is not a real proposal, because there are way too many
places it intrudes on, and you wouldn't be able to define a generator which
is also a callable. That said...
Slicing a list is fundamentally different from slicing an iterable. One
changes state, necessarily. Every time you say "foo[:2]", it will give a
different result, until you get no result at all.
Instead, I'll write it "foo(:2)", and ignore the fact that that's what
functions look like, and whether we CAN extend function syntax to make this
legal. Using parens reflects the syntax difference between list
comprehensions and generator expressions.
On Mar 21, 2016 7:36 PM, "Chris Angelico" <rosuav(a)gmail.com> wrote:
> On Tue, Mar 22, 2016 at 10:06 AM, Michel Desmoulin
> <desmoulinmichel(a)gmail.com> wrote:
> > Make slicing accept callables
> > =============================
> > So my first proposal is to be able to do:
> > def stop(element):
> > return element > 4
> > print(numbers[:stop])
> > It's quite pythonic, easy to understand : the end of the slice is when
> > this condition is met. Any not the strange way takewhile work, which is
> > "carry on as long as this condition is met".
> > We could also extend itertools.islice to accept such parameter.
I like this. I don't think it should happen, due to existing parts of the
language it might step on, but I like it.
foo(f:g:h) will mean
filter(h, takewhile(g, dropwhile(negate(f), foo)))
(possibly clearer if we imagine being able to write:
def negate_f(*args, **kwargs):
return not f(*args, **kwargs)
> > Slicing any iterable
> > ======================
> > So the second proposal is to allow:
> > def func_accepting_any_iterable(foo):
> > return bar(foo[3:7])
> > The slicing would then return a list if it's a list, a typle if it's a
> > tuple, and a islice(generator) if it's a generator. If somebody uses a
> > negative index, it would then raises a ValueError like islice.
> > This would make duck typing and iteration even easier in Python.
> Again, while I am sympathetic to the problem, it's actually very hard;
> islice always returns the same kind of thing, but slicing syntax can
> return all manner of different things, because it's up to the object
> on the left:
What if `foo(3:5)` always returned a lazy iterator? (Then `iter(o)` ==