Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.python > #106219 > unrolled thread

Strange range

Started byMarko Rauhamaa <marko@pacujo.net>
First post2016-04-01 16:15 +0300
Last post2016-04-01 08:52 -0600
Articles 16 on this page of 36 — 13 participants

Back to article view | Back to comp.lang.python


Contents

  Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 16:15 +0300
    Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-02 00:24 +1100
    Re: Strange range Steven D'Aprano <steve@pearwood.info> - 2016-04-02 00:26 +1100
      Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 17:12 +0300
        Re: Strange range Random832 <random832@fastmail.com> - 2016-04-01 10:39 -0400
      Re: Strange range Fabien <fabien.maussion@gmail.com> - 2016-04-01 16:16 +0200
        Re: Strange range Jussi Piitulainen <jussi.piitulainen@helsinki.fi> - 2016-04-01 17:28 +0300
        Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-02 01:31 +1100
          Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 17:34 +0300
            Re: Strange range Jussi Piitulainen <jussi.piitulainen@helsinki.fi> - 2016-04-01 17:44 +0300
            Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-02 01:45 +1100
              Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 18:43 +0300
            Re: Strange range Erik <python@lucidity.plus.com> - 2016-04-01 20:58 +0100
              Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 23:14 +0300
                Re: Strange range Rob Gaddi <rgaddi@highlandtechnology.invalid> - 2016-04-01 20:21 +0000
                  Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 23:44 +0300
                Re: Strange range Steven D'Aprano <steve@pearwood.info> - 2016-04-02 21:09 +1100
                  Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-02 13:48 +0300
            Re: Strange range Ned Batchelder <ned@nedbatchelder.com> - 2016-04-02 12:47 -0700
              Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-02 23:44 +0300
                Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-03 07:05 +1000
                  Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-03 00:40 +0300
                    Re: Strange range Ned Batchelder <ned@nedbatchelder.com> - 2016-04-02 14:50 -0700
                    Re: Strange range Stephen Hansen <me+python@ixokai.io> - 2016-04-02 23:43 -0700
                      Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-03 09:58 +0300
                        Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-03 17:10 +1000
                        Re: Strange range Ethan Furman <ethan@stoneleaf.us> - 2016-04-03 09:28 -0700
                        Re: Strange range Mark Lawrence <breamoreboy@yahoo.co.uk> - 2016-04-04 13:21 +0100
                    Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-03 17:08 +1000
                Re: Strange range Steven D'Aprano <steve@pearwood.info> - 2016-04-03 14:43 +1000
                  Re: Strange range Random832 <random832@fastmail.com> - 2016-04-03 01:20 -0400
                  Re: Strange range Steven D'Aprano <steve@pearwood.info> - 2016-04-03 15:28 +1000
        Re: Strange range Marko Rauhamaa <marko@pacujo.net> - 2016-04-01 17:32 +0300
    Re: Strange range Random832 <random832@fastmail.com> - 2016-04-01 10:42 -0400
    Re: Strange range Chris Angelico <rosuav@gmail.com> - 2016-04-02 01:50 +1100
    Re: Strange range Ian Kelly <ian.g.kelly@gmail.com> - 2016-04-01 08:52 -0600

Page 2 of 2 — ← Prev page 1 [2]


#106312

FromChris Angelico <rosuav@gmail.com>
Date2016-04-03 07:05 +1000
Message-ID<mailman.375.1459631138.28225.python-list@python.org>
In reply to#106310
On Sun, Apr 3, 2016 at 6:44 AM, Marko Rauhamaa <marko@pacujo.net> wrote:
> I don't have a problem with a list being a "reiterable." I only was
> surprised about range(), which I had thought to be a plain,
> down-to-earth iterator. There's barely any other practical use for a
> range, I believe.

That's Blub's Paradox right there. There are lots of other uses for
range(), but you just haven't used them.

ChrisA

[toc] | [prev] | [next] | [standalone]


#106313

FromMarko Rauhamaa <marko@pacujo.net>
Date2016-04-03 00:40 +0300
Message-ID<87vb3zpu49.fsf@elektro.pacujo.net>
In reply to#106312
Chris Angelico <rosuav@gmail.com>:

> On Sun, Apr 3, 2016 at 6:44 AM, Marko Rauhamaa <marko@pacujo.net> wrote:
>> I don't have a problem with a list being a "reiterable." I only was
>> surprised about range(), which I had thought to be a plain,
>> down-to-earth iterator. There's barely any other practical use for a
>> range, I believe.
>
> That's Blub's Paradox right there. There are lots of other uses for
> range(), but you just haven't used them.

That's why I was looking for counterexamples in the standard library
sources but couldn't really spot any (apart from a single
reversed(range())). Maybe I wasn't looking carefully enough.

As far as I can tell, range() is simply Python's way of implementing
classical integral "for" loops.


Marko

[toc] | [prev] | [next] | [standalone]


#106315

FromNed Batchelder <ned@nedbatchelder.com>
Date2016-04-02 14:50 -0700
Message-ID<b616d486-eab4-48da-8dc9-9054f3f7a6c7@googlegroups.com>
In reply to#106313
On Saturday, April 2, 2016 at 5:40:35 PM UTC-4, Marko Rauhamaa wrote:
> Chris Angelico <rosuav@gmail.com>:
> 
> > On Sun, Apr 3, 2016 at 6:44 AM, Marko Rauhamaa <marko@pacujo.net> wrote:
> >> I don't have a problem with a list being a "reiterable." I only was
> >> surprised about range(), which I had thought to be a plain,
> >> down-to-earth iterator. There's barely any other practical use for a
> >> range, I believe.
> >
> > That's Blub's Paradox right there. There are lots of other uses for
> > range(), but you just haven't used them.
> 
> That's why I was looking for counterexamples in the standard library
> sources but couldn't really spot any (apart from a single
> reversed(range())). Maybe I wasn't looking carefully enough.
> 
> As far as I can tell, range() is simply Python's way of implementing
> classical integral "for" loops.

You can easily use range in my double-loop example, or a variant:

    def pairs(n):
        nums = range(n)
        for i in nums:
            for j in nums:
                yield i, j

More importantly, range can be useful as an argument to a function that
doesn't realize it's receiving a range, as in the better way to implement
pairs:

    from itertools import product

    def pairs(n):
        return product(range(n), repeat=2)

By making range an iterable like lots of other things, it's more useful
in these kinds of compositional situations.

--Ned.

[toc] | [prev] | [next] | [standalone]


#106351

FromStephen Hansen <me+python@ixokai.io>
Date2016-04-02 23:43 -0700
Message-ID<mailman.391.1459665795.28225.python-list@python.org>
In reply to#106313
On Sat, Apr 2, 2016, at 02:40 PM, Marko Rauhamaa wrote:
> That's why I was looking for counterexamples in the standard library

This entire bent of an argument seems flawed to me.

The standard library has never been a beacon for best practices or
idiomatic uses of Python. That a use exists in the standard library, or
that one does not, doesn't really tell you anything meaningful about
Python itself or good practices with the language. The standard library
is under uniquely conservative constraints that enshrine compatibility
and reliability from one point release to another over any kind of
innovation. 

That code exists in the standard library is, itself, an incredibly
strong reason why it should stay as IS: changes for style, idiom, best
practices, modern techniques, those are all valid but *weak* arguments
to change the standard library. 

The stdlib works and its continuing to work tomorrow is its most
important burden. Just look at how much of the stdlib is not PEP8
compliant. Changing it to be PEP8 compliant is seen as a worse thing to
do then the possibility of introducing bugs by doing such a sweeping
change in the interest of good practices and style.

The stdlib exists as a bastion of stability above all else. Its
standards aren't a reason to make a change (or, not to make a change,
either). That doesn't mean its not useful to look at the standard
library, but you should not enshrine it as the example of good or
idiomatic code to measure decisions against. Most code exists outside
the stdlib. 

---
Stephen Hansen
  m e @ i x o k a i . i o

[toc] | [prev] | [next] | [standalone]


#106352

FromMarko Rauhamaa <marko@pacujo.net>
Date2016-04-03 09:58 +0300
Message-ID<87shz3p4a5.fsf@elektro.pacujo.net>
In reply to#106351
Stephen Hansen <me+python@ixokai.io>:

> On Sat, Apr 2, 2016, at 02:40 PM, Marko Rauhamaa wrote:
>> That's why I was looking for counterexamples in the standard library
>
> This entire bent of an argument seems flawed to me.
>
> The standard library has never been a beacon for best practices or
> idiomatic uses of Python.

It's an obvious corpus of Python code not written by me that's readily
available on my computer. An argument was made that range() has varied
uses. I was trying to find those varied uses.

> That a use exists in the standard library, or that one does not,
> doesn't really tell you anything meaningful about Python itself or
> good practices with the language. The standard library is under
> uniquely conservative constraints that enshrine compatibility and
> reliability from one point release to another over any kind of
> innovation.

What you seem to be saying is that range() used to be an iterator but
has since ascended to the status of an iterable.

> Most code exists outside the stdlib.

Which should then make it easy for you to point out the kinds of
counterexamples I was looking for.


Marko

[toc] | [prev] | [next] | [standalone]


#106354

FromChris Angelico <rosuav@gmail.com>
Date2016-04-03 17:10 +1000
Message-ID<mailman.393.1459667451.28225.python-list@python.org>
In reply to#106352
On Sun, Apr 3, 2016 at 4:58 PM, Marko Rauhamaa <marko@pacujo.net> wrote:
>> That a use exists in the standard library, or that one does not,
>> doesn't really tell you anything meaningful about Python itself or
>> good practices with the language. The standard library is under
>> uniquely conservative constraints that enshrine compatibility and
>> reliability from one point release to another over any kind of
>> innovation.
>
> What you seem to be saying is that range() used to be an iterator but
> has since ascended to the status of an iterable.

No, range() has never returned an iterator. In Python 2, it returned a
list, which is iterable. In Python 3, it returns a range object, which
is iterable. And in Python 2, xrange returns an xrange object, which
is also iterable (but less functional than the Py3 range object). None
of these is an iterator.

ChrisA

[toc] | [prev] | [next] | [standalone]


#106376

FromEthan Furman <ethan@stoneleaf.us>
Date2016-04-03 09:28 -0700
Message-ID<mailman.398.1459700859.28225.python-list@python.org>
In reply to#106352
On 04/02/2016 11:58 PM, Marko Rauhamaa wrote:
> Stephen Hansen <me+python@ixokai.io>:
>
>> On Sat, Apr 2, 2016, at 02:40 PM, Marko Rauhamaa wrote:
>>> That's why I was looking for counterexamples in the standard library
>>
>> This entire bent of an argument seems flawed to me.
>>
>> The standard library has never been a beacon for best practices or
>> idiomatic uses of Python.
>
> It's an obvious corpus of Python code not written by me that's readily
> available on my computer. An argument was made that range() has varied
> uses. I was trying to find those varied uses.

Which is fine, but failing to find them is insignificant.


>> Most code exists outside the stdlib.
>
> Which should then make it easy for you to point out the kinds of
> counterexamples I was looking for.

I'm pretty sure that 99+% of the non-stdlib code out there is also 
completely inaccessible (or at least inconveniently accessible) to 
Stephen as well.

Besides which, the amount of extra effort someone else is willing to go 
to to prove something is directly related to the interestingness of the 
topic -- and the various uses of range() isn't that interesting (it 
would be more interesting if a PEP was on the line...) .

--
~Ethan~

[toc] | [prev] | [next] | [standalone]


#106437

FromMark Lawrence <breamoreboy@yahoo.co.uk>
Date2016-04-04 13:21 +0100
Message-ID<mailman.15.1459772490.32530.python-list@python.org>
In reply to#106352
On 03/04/2016 17:28, Ethan Furman wrote:
> On 04/02/2016 11:58 PM, Marko Rauhamaa wrote:
>> Stephen Hansen <me+python@ixokai.io>:
>
> I'm pretty sure that 99+% of the non-stdlib code out there is also
> completely inaccessible (or at least inconveniently accessible) to
> Stephen as well.
>

http://nullege.com/codes/search?cq=range would appear to be as good a 
starting point as any.

-- 
My fellow Pythonistas, ask not what our language can do for you, ask
what you can do for our language.

Mark Lawrence

[toc] | [prev] | [next] | [standalone]


#106353

FromChris Angelico <rosuav@gmail.com>
Date2016-04-03 17:08 +1000
Message-ID<mailman.392.1459667304.28225.python-list@python.org>
In reply to#106313
On Sun, Apr 3, 2016 at 4:43 PM, Stephen Hansen <me+python@ixokai.io> wrote:
> The stdlib exists as a bastion of stability above all else. Its
> standards aren't a reason to make a change (or, not to make a change,
> either). That doesn't mean its not useful to look at the standard
> library, but you should not enshrine it as the example of good or
> idiomatic code to measure decisions against. Most code exists outside
> the stdlib.

Expanding on this: There have been times when the stdlib has been
cited in proposals, such as the introduction of a new keyword. Out of
five plausible words, two have significant use in the stdlib, another
has a couple of uses, and two more have no references at all. Specific
example from PEP 359 [1]; the same line of analysis has also been used
elsewhere. Also, a proposed new syntax can attempt to justify its
benefit by taking examples from the stdlib, not because they will
necessarily be changed, but simply because it's a good-sized codebase
that all Python devs and tinkerers will have easy access to. PEP 463
[2] demonstrates this. Similarly, but in reverse: The stdlib can
provide examples showing how a proposal will _break_ existing code,
and how it should be fixed; PEP 479 [3] has a few examples, some from
the stdlib, some hypothetical. In each case, the stdlib is being
treated as simply "a body of Python code", and one which has a measure
of neutrality (we're not favouring web app developers by looking at
the Django source code, or numeric computational work by looking at
Pandas, or anything like that), and if anything, it's indicative of
older codebases rather than newer ones, which is usually good for
proposals that need to be conservative.

So in the case of range() usage, I would say that stdlib usage showing
"x in range(...)" would be highly significant, but *absence* of such
usage is not.

ChrisA

[1] https://www.python.org/dev/peps/pep-0359/#keyword
[2] https://www.python.org/dev/peps/pep-0463/#example-usage
[3] https://www.python.org/dev/peps/pep-0479/#examples-of-breakage

[toc] | [prev] | [next] | [standalone]


#106345

FromSteven D'Aprano <steve@pearwood.info>
Date2016-04-03 14:43 +1000
Message-ID<57009f91$0$1612$c3e8da3$5496439d@news.astraweb.com>
In reply to#106310
On Sun, 3 Apr 2016 06:44 am, Marko Rauhamaa wrote:

> I don't have a problem with a list being a "reiterable." I only was
> surprised about range(), which I had thought to be a plain,
> down-to-earth iterator. There's barely any other practical use for a
> range, I believe.

I can understand that you were mistaken. It's an easy mistake to make.

But I don't understand why you seem to be insisting that its somehow a flaw
that (x)range is implemented as a "lazy list" instead of an iterator.

If you want an iterator, it's only a single function call away: iter(r).

In the meantime, range objects provide the full sequence API. They're not
quite full lists, as they don't allow arbitrary orderings or arbitrary
items, so any list method which implies that arbitrary items can be
inserted or deleted are not included.

It also acts as a proof of concept that Python supports intelligent, lazy
objects that can produce values on demand.

If you personally don't see any advantage in this, so be it, but you might
not be aware of the history of (x)range:

Guido in 2001: "Nobody uses this extra functionality, and its buggy, let's
get rid of it."

https://www.python.org/dev/peps/pep-0260/

Feature request in 2004: "Membership testing in xrange objects is horribly
slow. Let's add a __contains__ method."

http://bugs.python.org/issue1002085

(Request rejected, because the __contains__ method was removed in 2002.)

Discussion and feature request in 2007: "We really ought to fix that slow
performance of (x)range membership testing..."

http://bugs.python.org/issue1766304


So it's one of those things on the border of useful or not. Those who use
it, miss it when its gone. Those who don't, don't understand why anyone
wants it.



-- 
Steven

[toc] | [prev] | [next] | [standalone]


#106347

FromRandom832 <random832@fastmail.com>
Date2016-04-03 01:20 -0400
Message-ID<mailman.389.1459660855.28225.python-list@python.org>
In reply to#106345
On Sun, Apr 3, 2016, at 00:43, Steven D'Aprano wrote:
> If you personally don't see any advantage in this, so be it, but you
> might
> not be aware of the history of (x)range:
> 
> Guido in 2001: "Nobody uses this extra functionality, and its buggy,
> let's
> get rid of it."
> 
> https://www.python.org/dev/peps/pep-0260/

Several of those features apparently never did come back. The repeat
count never did (you can't multiply ranges now), and it occurs to me
that slicing a range that has a repeat count is intractable:
(range(3)*2)[1:5] should yield 1, 2, 0, 1, which can't be represented as
a range object. It also doesn't support comparison operations.

[toc] | [prev] | [next] | [standalone]


#106348

FromSteven D'Aprano <steve@pearwood.info>
Date2016-04-03 15:28 +1000
Message-ID<5700aa13$0$1606$c3e8da3$5496439d@news.astraweb.com>
In reply to#106345
On Sun, 3 Apr 2016 02:43 pm, Steven D'Aprano wrote:

> If you personally don't see any advantage in this, so be it, but you might
> not be aware of the history of (x)range:
> 
> Guido in 2001: "..."

Correction: these are not direct quotes, but paraphrases. My apologies for
any confusion.


-- 
Steven

[toc] | [prev] | [next] | [standalone]


#106228

FromMarko Rauhamaa <marko@pacujo.net>
Date2016-04-01 17:32 +0300
Message-ID<87pou9jt6k.fsf@elektro.pacujo.net>
In reply to#106224
Fabien <fabien.maussion@gmail.com>:

> On 04/01/2016 03:26 PM, Steven D'Aprano wrote:
>> Incorrect. range is a lazy sequence.
>
> But how does range "know" that it has to start from scratch again?

The "for .. in" statement invokes the __iter__() method of the iterable
object to get an iterator (maybe via the builtin iter() function).

Iterators have an __iter__() method as well which returns the iterator
itself.

Thus,

   >>> it = iter(range(10))
   >>> it is iter(it)
   True


Marko

[toc] | [prev] | [next] | [standalone]


#106232

FromRandom832 <random832@fastmail.com>
Date2016-04-01 10:42 -0400
Message-ID<mailman.313.1459521732.28225.python-list@python.org>
In reply to#106219
On Fri, Apr 1, 2016, at 09:24, Chris Angelico wrote:
> It is an iterable. It is not a factory, as that implies that you call
> it.

I do have an objection to this statement. It's perfectly reasonable to
describe the factory pattern as applying to objects on which you call a
method to return the new object you are interested in. In this sense,
all collections are iterator factories.

[toc] | [prev] | [next] | [standalone]


#106235

FromChris Angelico <rosuav@gmail.com>
Date2016-04-02 01:50 +1100
Message-ID<mailman.315.1459522215.28225.python-list@python.org>
In reply to#106219
On Sat, Apr 2, 2016 at 1:42 AM, Random832 <random832@fastmail.com> wrote:
> On Fri, Apr 1, 2016, at 09:24, Chris Angelico wrote:
>> It is an iterable. It is not a factory, as that implies that you call
>> it.
>
> I do have an objection to this statement. It's perfectly reasonable to
> describe the factory pattern as applying to objects on which you call a
> method to return the new object you are interested in. In this sense,
> all collections are iterator factories.

Hmm. I suppose that would be reasonable, if you expect to call
range_object.__iter__() - but you shouldn't. You should call
iter(range_object), which, to my mind, means that *iter* is an
iterator factory.

Anyway, the word "iterable" accurately sums up the state: it's a thing
you can iterate over.

ChrisA

[toc] | [prev] | [next] | [standalone]


#106236

FromIan Kelly <ian.g.kelly@gmail.com>
Date2016-04-01 08:52 -0600
Message-ID<mailman.316.1459522390.28225.python-list@python.org>
In reply to#106219
On Fri, Apr 1, 2016 at 8:42 AM, Random832 <random832@fastmail.com> wrote:
> On Fri, Apr 1, 2016, at 09:24, Chris Angelico wrote:
>> It is an iterable. It is not a factory, as that implies that you call
>> it.
>
> I do have an objection to this statement. It's perfectly reasonable to
> describe the factory pattern as applying to objects on which you call a
> method to return the new object you are interested in. In this sense,
> all collections are iterator factories.

I think the problem with that is that it implies something about the
purpose of the object. Usually when we talk about the factory pattern,
we're talking about an object that creates instances of something and
does nothing else. So in that sense it's misleading to refer to dict
or list or even range objects as "iterator factories", because they
also do a lot of other things that are equally if not more important.

[toc] | [prev] | [standalone]


Page 2 of 2 — ← Prev page 1 [2]

Back to top | Article view | comp.lang.python


csiph-web