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


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

singleton ... again

Started byAsaf Las <roegltd@gmail.com>
First post2014-02-11 20:34 -0800
Last post2014-02-12 15:05 -0700
Articles 20 on this page of 40 — 15 participants

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


Contents

  singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-11 20:34 -0800
    Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-11 21:15 -0800
    Re:singleton ... again Dave Angel <davea@davea.name> - 2014-02-12 00:48 -0500
      Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-12 00:55 -0500
        Re: singleton ... again Gregory Ewing <greg.ewing@canterbury.ac.nz> - 2014-02-12 23:04 +1300
          Re: singleton ... again Ben Finney <ben+python@benfinney.id.au> - 2014-02-12 21:09 +1100
            Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-12 08:40 -0500
            Re: singleton ... again Piet van Oostrum <piet@vanoostrum.org> - 2014-02-13 10:00 +0100
              Re: singleton ... again Ned Batchelder <ned@nedbatchelder.com> - 2014-02-13 06:50 -0500
              Re: singleton ... again Chris Angelico <rosuav@gmail.com> - 2014-02-13 22:57 +1100
                Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-13 10:24 -0500
                  Re: singleton ... again Chris Angelico <rosuav@gmail.com> - 2014-02-14 07:03 +1100
                  Re: singleton ... again Robert Kern <robert.kern@gmail.com> - 2014-02-13 21:13 +0000
                  Re: singleton ... again Chris Angelico <rosuav@gmail.com> - 2014-02-14 08:27 +1100
              Re: singleton ... again Ethan Furman <ethan@stoneleaf.us> - 2014-02-13 08:57 -0800
                Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-13 12:57 -0500
                  Re: singleton ... again Ethan Furman <ethan@stoneleaf.us> - 2014-02-13 10:31 -0800
                    Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-13 14:03 -0500
                      Re: singleton ... again Chris Angelico <rosuav@gmail.com> - 2014-02-14 06:50 +1100
                      Re: singleton ... again Grant Edwards <invalid@invalid.invalid> - 2014-02-13 22:28 +0000
                Re: singleton ... again Gregory Ewing <greg.ewing@canterbury.ac.nz> - 2014-02-14 18:21 +1300
              Re: singleton ... again Tim Delaney <timothy.c.delaney@gmail.com> - 2014-02-14 06:16 +1100
          Re: singleton ... again Steven D'Aprano <steve@pearwood.info> - 2014-02-13 02:58 +0000
            Re: singleton ... again Ben Finney <ben+python@benfinney.id.au> - 2014-02-13 14:07 +1100
              Re: singleton ... again Steven D'Aprano <steve@pearwood.info> - 2014-02-13 04:24 +0000
                Re: singleton ... again Chris Angelico <rosuav@gmail.com> - 2014-02-13 15:33 +1100
                Re: singleton ... again Gregory Ewing <greg.ewing@canterbury.ac.nz> - 2014-02-14 18:15 +1300
            Re: singleton ... again Gregory Ewing <greg.ewing@canterbury.ac.nz> - 2014-02-14 18:06 +1300
      Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 09:50 -0800
        Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 09:56 -0800
          Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 09:58 -0800
          Re: singleton ... again Gregory Ewing <greg.ewing@canterbury.ac.nz> - 2014-02-13 10:57 +1300
            Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 17:38 -0800
        Re: singleton ... again Mark Lawrence <breamoreboy@yahoo.co.uk> - 2014-02-12 18:57 +0000
          Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 17:02 -0800
        Re: singleton ... again Ned Batchelder <ned@nedbatchelder.com> - 2014-02-12 16:34 -0500
          Re: singleton ... again Asaf Las <roegltd@gmail.com> - 2014-02-12 17:34 -0800
        Re: singleton ... again Tim Delaney <timothy.c.delaney@gmail.com> - 2014-02-13 10:08 +1100
        Re: singleton ... again Roy Smith <roy@panix.com> - 2014-02-12 20:57 -0500
    Re: singleton ... again Michael Torrie <torriem@gmail.com> - 2014-02-12 15:05 -0700

Page 1 of 2  [1] 2  Next page →


#65995 — singleton ... again

FromAsaf Las <roegltd@gmail.com>
Date2014-02-11 20:34 -0800
Subjectsingleton ... again
Message-ID<fdbb58a7-87c0-4a2f-bedf-f8e3e14fa356@googlegroups.com>
playing a bit with subject. 

pros and cons of this approach? did i create bicycle again? :-)

class myclass(object):
    class_instance = None
    
    def __new__(cls, *args, **kwargs):
        if myclass.class_instance == None:
            return object.__new__(cls)
        return myclass.class_instance

    def __init__(self, some):
        if self.__class__.class_instance == None: # init blocker 
            self.__class__.class_instance = self
            self.member = some
    
    def __del__(self):
        self.__class__.class_instance = None
    
one_class = myclass(1)
print(id(one_class), one_class.member )

two_class = myclass(2)
print(id(two_class), two_class.member)

[toc] | [next] | [standalone]


#65997

FromAsaf Las <roegltd@gmail.com>
Date2014-02-11 21:15 -0800
Message-ID<d1748b1f-bbe0-482d-97dd-492318d68283@googlegroups.com>
In reply to#65995
there is error should assign weakref to class static member otherwise __del__ 
will never be called. 

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


#65999

FromDave Angel <davea@davea.name>
Date2014-02-12 00:48 -0500
Message-ID<mailman.6728.1392183929.18130.python-list@python.org>
In reply to#65995
 Asaf Las <roegltd@gmail.com> Wrote in message:
> playing a bit with subject. 
> 
> pros and cons of this approach? did i create bicycle again? :-)
> 
> class myclass(object):
>     class_instance = None
>     
>     def __new__(cls, *args, **kwargs):
>         if myclass.class_instance == None:
>             return object.__new__(cls)
>         return myclass.class_instance
> 
>     def __init__(self, some):
>         if self.__class__.class_instance == None: # init blocker 
>             self.__class__.class_instance = self
>             self.member = some
>     
>     def __del__(self):
>         self.__class__.class_instance = None
>     
> one_class = myclass(1)
> print(id(one_class), one_class.member )
> 
> two_class = myclass(2)
> print(id(two_class), two_class.member)
> 
> 

Perhaps if you would state your actual goal,  we could judge
 whether this code is an effective way to accomplish
 it.


-- 
DaveA

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


#66000

FromRoy Smith <roy@panix.com>
Date2014-02-12 00:55 -0500
Message-ID<roy-11BAB5.00555912022014@news.panix.com>
In reply to#65999
In article <mailman.6728.1392183929.18130.python-list@python.org>,
 Dave Angel <davea@davea.name> wrote:

>  Asaf Las <roegltd@gmail.com> Wrote in message:
> > playing a bit with subject. 
> > 
> > pros and cons of this approach? did i create bicycle again? :-)
> > 
> > class myclass(object):
> >     class_instance = None
> >     
> >     def __new__(cls, *args, **kwargs):
> >         if myclass.class_instance == None:
> >             return object.__new__(cls)
> >         return myclass.class_instance
> > 
> >     def __init__(self, some):
> >         if self.__class__.class_instance == None: # init blocker 
> >             self.__class__.class_instance = self
> >             self.member = some
> >     
> >     def __del__(self):
> >         self.__class__.class_instance = None
> >     
> > one_class = myclass(1)
> > print(id(one_class), one_class.member )
> > 
> > two_class = myclass(2)
> > print(id(two_class), two_class.member)
> > 
> > 
> 
> Perhaps if you would state your actual goal,  we could judge
>  whether this code is an effective way to accomplish
>  it.

It looks to me like he's trying to implement a classic Gang of Four 
singleton pattern.

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


#66022

FromGregory Ewing <greg.ewing@canterbury.ac.nz>
Date2014-02-12 23:04 +1300
Message-ID<bm0v9iFpuquU1@mid.individual.net>
In reply to#66000
Roy Smith wrote:
> It looks to me like he's trying to implement a classic Gang of Four 
> singleton pattern.

Which I've never really seen the point of in Python,
or any other language for that matter. Just create
one instance of the class during initialisation,
put it in a global somewhere, and use it thereafter.

If you really want to make sure nobody creates
another instance by accident, delete the class
out of the namespace after instantiating it.

-- 
Greg

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


#66024

FromBen Finney <ben+python@benfinney.id.au>
Date2014-02-12 21:09 +1100
Message-ID<mailman.6750.1392199807.18130.python-list@python.org>
In reply to#66022
Gregory Ewing <greg.ewing@canterbury.ac.nz> writes:

> Roy Smith wrote:
> > It looks to me like he's trying to implement a classic Gang of Four
> > singleton pattern.
>
> Which I've never really seen the point of in Python, or any other
> language for that matter. Just create one instance of the class during
> initialisation, put it in a global somewhere, and use it thereafter.

Make that “somewhere” a module namespace, and you effectively have a
Singleton for all practical purposes. So yes, I see the point of it; but
we already have it built in :-)

-- 
 \     “To save the world requires faith and courage: faith in reason, |
  `\            and courage to proclaim what reason shows to be true.” |
_o__)                                                —Bertrand Russell |
Ben Finney

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


#66033

FromRoy Smith <roy@panix.com>
Date2014-02-12 08:40 -0500
Message-ID<roy-828BCA.08403012022014@news.panix.com>
In reply to#66024
In article <mailman.6750.1392199807.18130.python-list@python.org>,
 Ben Finney <ben+python@benfinney.id.au> wrote:

> Gregory Ewing <greg.ewing@canterbury.ac.nz> writes:
> 
> > Roy Smith wrote:
> > > It looks to me like he's trying to implement a classic Gang of Four
> > > singleton pattern.
> >
> > Which I've never really seen the point of in Python, or any other
> > language for that matter. Just create one instance of the class during
> > initialisation, put it in a global somewhere, and use it thereafter.
> 
> Make that “somewhere” a module namespace, and you effectively have a
> Singleton for all practical purposes. So yes, I see the point of it; but
> we already have it built in :-)

This is one of the big problems with the Gang of Four book (and most of 
the pattern literature).  They present these patterns as universal to 
all OOPL's, when in reality, so much of them is "Things I need to do to 
appease the C++ compiler".

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


#66159

FromPiet van Oostrum <piet@vanoostrum.org>
Date2014-02-13 10:00 +0100
Message-ID<m2a9dvmlos.fsf@cochabamba.vanoostrum.org>
In reply to#66024
Ben Finney <ben+python@benfinney.id.au> writes:

> Gregory Ewing <greg.ewing@canterbury.ac.nz> writes:
>
>> Roy Smith wrote:
>> > It looks to me like he's trying to implement a classic Gang of Four
>> > singleton pattern.
>>
>> Which I've never really seen the point of in Python, or any other
>> language for that matter. Just create one instance of the class during
>> initialisation, put it in a global somewhere, and use it thereafter.
>
> Make that “somewhere” a module namespace, and you effectively have a
> Singleton for all practical purposes. So yes, I see the point of it; but
> we already have it built in :-)

There is a use case for a singleton class: when creating the singleton
object takes considerable resources and you don't need it always in your
program.
-- 
Piet van Oostrum <piet@vanoostrum.org>
WWW: http://pietvanoostrum.com/
PGP key: [8DAE142BE17999C4]

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


#66166

FromNed Batchelder <ned@nedbatchelder.com>
Date2014-02-13 06:50 -0500
Message-ID<mailman.6831.1392292254.18130.python-list@python.org>
In reply to#66159
On 2/13/14 4:00 AM, Piet van Oostrum wrote:
> Ben Finney <ben+python@benfinney.id.au> writes:
>
>> Gregory Ewing <greg.ewing@canterbury.ac.nz> writes:
>>
>>> Roy Smith wrote:
>>>> It looks to me like he's trying to implement a classic Gang of Four
>>>> singleton pattern.
>>>
>>> Which I've never really seen the point of in Python, or any other
>>> language for that matter. Just create one instance of the class during
>>> initialisation, put it in a global somewhere, and use it thereafter.
>>
>> Make that “somewhere” a module namespace, and you effectively have a
>> Singleton for all practical purposes. So yes, I see the point of it; but
>> we already have it built in :-)
>
> There is a use case for a singleton class: when creating the singleton
> object takes considerable resources and you don't need it always in your
> program.
>

I still don't see it.  To convince me that a singleton class makes 
sense, you'd have to explain why by virtue of the class's very nature, 
it never makes sense for there ever to be more than one of them.

Your example is an expensive-to-create object.  Why does that mean I 
might not want two of them?  I can see how it makes sense to have a 
factory function, which will make one only when asked, and will hold 
onto that object for the next time it's needed.

But that's different than a class which pretends to make instances but 
actually always returns the same instance.

-- 
Ned Batchelder, http://nedbatchelder.com

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


#66170

FromChris Angelico <rosuav@gmail.com>
Date2014-02-13 22:57 +1100
Message-ID<mailman.6834.1392292646.18130.python-list@python.org>
In reply to#66159
On Thu, Feb 13, 2014 at 10:50 PM, Ned Batchelder <ned@nedbatchelder.com> wrote:
> I still don't see it.  To convince me that a singleton class makes sense,
> you'd have to explain why by virtue of the class's very nature, it never
> makes sense for there ever to be more than one of them.

There's a huge difference, btw, between mutable and immutable
singletons. With immutables like None, True/False, integers, strings,
and tuples thereof, returning a preexisting object is just an
optimization. Do it if you want, don't if you don't, nobody's going to
hugely care. With mutables, it's hugely different. A singleton
"database connection" object would, imo, be hugely confusing; you'd
think you created a separate connection object, but no, what you do on
this one affects the other. Better there to have module-level
functions; at least Python programmers should understand that
reimporting a module gives you back another reference to the same
module.

ChrisA

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


#66185

FromRoy Smith <roy@panix.com>
Date2014-02-13 10:24 -0500
Message-ID<roy-141A69.10240713022014@news.panix.com>
In reply to#66170
In article <mailman.6834.1392292646.18130.python-list@python.org>,
 Chris Angelico <rosuav@gmail.com> wrote:

> On Thu, Feb 13, 2014 at 10:50 PM, Ned Batchelder <ned@nedbatchelder.com> 
> wrote:
> > I still don't see it.  To convince me that a singleton class makes sense,
> > you'd have to explain why by virtue of the class's very nature, it never
> > makes sense for there ever to be more than one of them.
> 
> There's a huge difference, btw, between mutable and immutable
> singletons. With immutables like None, True/False, integers, strings,
> and tuples thereof, returning a preexisting object is just an
> optimization. Do it if you want, don't if you don't, nobody's going to
> hugely care.

People *depend* on None being a singleton (and are encouraged to do so), 
when they use "is" as the test-for-Noneness.

> With mutables, it's hugely different. A singleton
> "database connection" object would, imo, be hugely confusing; you'd
> think you created a separate connection object, but no, what you do on
> this one affects the other.

Except that if you do caching in the database connector, you would 
certainly want the cache to be shared between all the users.  There's no 
right answer here.  Each way has it's advantages and disadvantages.  And 
it would only be confusing if the documentation didn't spell out which 
way it was doing it, leaving people to make (possibly wrong) assumptions.

> Better there to have module-level functions; at least Python 
> programmers should understand that reimporting a module gives you 
> back another reference to the same module.

Except when it doesn't.  Singleton-ness of modules depends on the names 
under which they were imported.  Symlinks, for example, can fool the 
import machinery.

$ ls -l s1 s2
lrwxrwxrwx 1 roy roy 1 Feb 13 10:13 s1 -> s
lrwxrwxrwx 1 roy roy 1 Feb 13 10:13 s2 -> s

$ ls -l s
total 12
-rw-rw-r-- 1 roy roy   0 Feb 13 10:13 __init__.py
-rw-rw-r-- 1 roy roy 101 Feb 13 10:14 __init__.pyc
-rw-rw-r-- 1 roy roy   9 Feb 13 10:12 singleton.py
-rw-rw-r-- 1 roy roy 123 Feb 13 10:14 singleton.pyc

>>> import s1.singleton
>>> import s2.singleton
>>> s1.singleton == s2.singleton
False

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


#66226

FromChris Angelico <rosuav@gmail.com>
Date2014-02-14 07:03 +1100
Message-ID<mailman.6869.1392321827.18130.python-list@python.org>
In reply to#66185
On Fri, Feb 14, 2014 at 2:24 AM, Roy Smith <roy@panix.com> wrote:
> In article <mailman.6834.1392292646.18130.python-list@python.org>,
>  Chris Angelico <rosuav@gmail.com> wrote:
>
>> On Thu, Feb 13, 2014 at 10:50 PM, Ned Batchelder <ned@nedbatchelder.com>
>> wrote:
>> > I still don't see it.  To convince me that a singleton class makes sense,
>> > you'd have to explain why by virtue of the class's very nature, it never
>> > makes sense for there ever to be more than one of them.
>>
>> There's a huge difference, btw, between mutable and immutable
>> singletons. With immutables like None, True/False, integers, strings,
>> and tuples thereof, returning a preexisting object is just an
>> optimization. Do it if you want, don't if you don't, nobody's going to
>> hugely care.
>
> People *depend* on None being a singleton (and are encouraged to do so),
> when they use "is" as the test-for-Noneness.

Circular argument, though. If None weren't a singleton, people would
use == to test for Noneness. Since it's been guaranteed to be
optimized to a singleton, the comparison can also be optimized, but
it's still just an optimization, as can be seen with integers. In
CPython, you could test for small integer equality using 'is', but
since that optimization isn't guaranteed, neither is that code
pattern.

>> With mutables, it's hugely different. A singleton
>> "database connection" object would, imo, be hugely confusing; you'd
>> think you created a separate connection object, but no, what you do on
>> this one affects the other.
>
> Except that if you do caching in the database connector, you would
> certainly want the cache to be shared between all the users.  There's no
> right answer here.  Each way has it's advantages and disadvantages.  And
> it would only be confusing if the documentation didn't spell out which
> way it was doing it, leaving people to make (possibly wrong) assumptions.

Compare these:

# Style 1:
import magicsql
import othermodule
conn = magicsql.MagicSQL("127.0.0.1")
conn.set_parameter("foobar", True)
othermodule.do_stuff()
conn.query("select foo from bar")

# Style 2:
import magicsql
import othermodule
magicsql.connect("127.0.0.1")
magicsql.set_parameter("foobar", True)
othermodule.do_stuff()
magicsql.query("select foo from bar")

Suppose othermodule.do_stuff() does the same sort of calls except that
it sets parameter foobar to False. With Style 1, I would expect that
conn is independent of any connection object used by othermodule, and
it would be a major source of bugs (look at PHP's persistent
connections and how extremely careful you have to be with changing
*any* connection settings). But with Style 2, it's obvious that anyone
else importing magicsql and changing parameters will affect me.

That's why module-level functions are the clearer way to do this than
singleton classes.

>> Better there to have module-level functions; at least Python
>> programmers should understand that reimporting a module gives you
>> back another reference to the same module.
>
> Except when it doesn't.  Singleton-ness of modules depends on the names
> under which they were imported.  Symlinks, for example, can fool the
> import machinery.
>
> $ ls -l s1 s2
> lrwxrwxrwx 1 roy roy 1 Feb 13 10:13 s1 -> s
> lrwxrwxrwx 1 roy roy 1 Feb 13 10:13 s2 -> s
>
> $ ls -l s
> total 12
> -rw-rw-r-- 1 roy roy   0 Feb 13 10:13 __init__.py
> -rw-rw-r-- 1 roy roy 101 Feb 13 10:14 __init__.pyc
> -rw-rw-r-- 1 roy roy   9 Feb 13 10:12 singleton.py
> -rw-rw-r-- 1 roy roy 123 Feb 13 10:14 singleton.pyc
>
>>>> import s1.singleton
>>>> import s2.singleton
>>>> s1.singleton == s2.singleton
> False

Sure, they're not a guarantee. And if you fork a subprocess, then you
have copies of the singleton, too. That's not the point here. If you
have two modules and each one types "import random", you would not be
surprised to learn that the name "random" in each is bound to the
exact same random, and that they effectively share state. If you're
calling random.random(), and then you call another module which
imports random and calls random.random(), you don't complain that your
sequence of random numbers was disrupted.

But if you were to get yourself a random.Random() instance and someone
else does the same, then the style of code makes it *look like* you
should be working with independent objects. And in the case of the
random module, that is exactly what happens. Instantiate? Separate.
Module-level functions? Shared.

ChrisA

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


#66244

FromRobert Kern <robert.kern@gmail.com>
Date2014-02-13 21:13 +0000
Message-ID<mailman.6885.1392326014.18130.python-list@python.org>
In reply to#66185
On 2014-02-13 20:03, Chris Angelico wrote:
> On Fri, Feb 14, 2014 at 2:24 AM, Roy Smith <roy@panix.com> wrote:
>> In article <mailman.6834.1392292646.18130.python-list@python.org>,
>>   Chris Angelico <rosuav@gmail.com> wrote:
>>
>>> On Thu, Feb 13, 2014 at 10:50 PM, Ned Batchelder <ned@nedbatchelder.com>
>>> wrote:
>>>> I still don't see it.  To convince me that a singleton class makes sense,
>>>> you'd have to explain why by virtue of the class's very nature, it never
>>>> makes sense for there ever to be more than one of them.
>>>
>>> There's a huge difference, btw, between mutable and immutable
>>> singletons. With immutables like None, True/False, integers, strings,
>>> and tuples thereof, returning a preexisting object is just an
>>> optimization. Do it if you want, don't if you don't, nobody's going to
>>> hugely care.
>>
>> People *depend* on None being a singleton (and are encouraged to do so),
>> when they use "is" as the test-for-Noneness.
>
> Circular argument, though. If None weren't a singleton, people would
> use == to test for Noneness. Since it's been guaranteed to be
> optimized to a singleton, the comparison can also be optimized, but
> it's still just an optimization, as can be seen with integers. In
> CPython, you could test for small integer equality using 'is', but
> since that optimization isn't guaranteed, neither is that code
> pattern.

We don't use `is None` instead of `== None` for the speed. We use it for 
robustness. We don't want arbitrary __eq__()s to interfere with our sentinel 
tests. If None weren't a singleton that we could use as such a sentinel, we'd 
make one.

-- 
Robert Kern

"I have come to believe that the whole world is an enigma, a harmless enigma
  that is made terrible by our own mad attempt to interpret it as though it had
  an underlying truth."
   -- Umberto Eco

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


#66251

FromChris Angelico <rosuav@gmail.com>
Date2014-02-14 08:27 +1100
Message-ID<mailman.6890.1392326879.18130.python-list@python.org>
In reply to#66185
On Fri, Feb 14, 2014 at 8:13 AM, Robert Kern <robert.kern@gmail.com> wrote:
> We don't use `is None` instead of `== None` for the speed. We use it for
> robustness. We don't want arbitrary __eq__()s to interfere with our sentinel
> tests. If None weren't a singleton that we could use as such a sentinel,
> we'd make one.

Sure. Yes, its identity is important as part of its being the Python
equivalent of C's null pointer. But the main point of singletons is to
be able to be "instantiated" without creating new elements; the
sentinel status of None is no different from the classic way of
recognizing the presence of an argument:

_SENTINEL = object()
def foo(arg1, arg2=_SENTINEL):
    if arg2 is not _SENTINEL: do_stuff_with(arg2)

That's not a singleton in that sense; it's just a unique object. You
could use [] for that instead of object() and it would work just the
same. So None is serving multiple purposes: it's an empty object, but
it's also a sentinel. In many uses, it wouldn't be a problem to have
more Nones floating around, hence it's mostly like your classic
singleton.

My main point about mutable vs immutable is more clearly seen with
integers and strings. Some integers are cached; some strings are
interned; nobody particularly cares about the exact boundaries, except
when playing around with id() or introspection of some sort.

ChrisA

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


#66194

FromEthan Furman <ethan@stoneleaf.us>
Date2014-02-13 08:57 -0800
Message-ID<mailman.6850.1392313443.18130.python-list@python.org>
In reply to#66159
On 02/13/2014 03:50 AM, Ned Batchelder wrote:
> On 2/13/14 4:00 AM, Piet van Oostrum wrote:
>> Ben Finney <ben+python@benfinney.id.au> writes:
>>
>>> Gregory Ewing <greg.ewing@canterbury.ac.nz> writes:
>>>
>>>> Roy Smith wrote:
>>>>> It looks to me like he's trying to implement a classic Gang of Four
>>>>> singleton pattern.
>>>>
>>>> Which I've never really seen the point of in Python, or any other
>>>> language for that matter. Just create one instance of the class during
>>>> initialisation, put it in a global somewhere, and use it thereafter.
>>>
>>> Make that “somewhere” a module namespace, and you effectively have a
>>> Singleton for all practical purposes. So yes, I see the point of it; but
>>> we already have it built in :-)
>>
>> There is a use case for a singleton class: when creating the singleton
>> object takes considerable resources and you don't need it always in your
>> program.
>>
>
> I still don't see it.  To convince me that a singleton class makes sense, you'd have to explain why by virtue of the
> class's very nature, it never makes sense for there ever to be more than one of them.

Say you have a database with a column that can only have a handful of values (like an enumeration, for instance) and 
this database can have hundreds of thousands of rows.  When you're working with all those rows at once having just one 
object for the third enum value is a useful optimization.

Say you have a class that represents serial ports or your computer.  You should get the same object every time you ask 
for SerialPort(2).

--
~Ethan~

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


#66197

FromRoy Smith <roy@panix.com>
Date2014-02-13 12:57 -0500
Message-ID<roy-640027.12574313022014@news.panix.com>
In reply to#66194
In article <mailman.6850.1392313443.18130.python-list@python.org>,
 Ethan Furman <ethan@stoneleaf.us> wrote:

> Say you have a class that represents serial ports or your computer.  You 
> should get the same object every time you ask 
> for SerialPort(2).

Why?  Certainly, you should get objects which refer to the same physical 
port.  So:

port_a = SerialPort(2)
port_b = SerialPort(2)

port_a.enable()
assert port_b.is_shutdown() == False

port_a.shutdown()
assert port_b.is_shutdown() == True

But, why do they have to be the same object?  Why should I care if

port_a is port_b

is False, as long as all operations I perform on either are reflected in 
correct state changes on the other one?

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


#66202

FromEthan Furman <ethan@stoneleaf.us>
Date2014-02-13 10:31 -0800
Message-ID<mailman.6852.1392317509.18130.python-list@python.org>
In reply to#66197
On 02/13/2014 09:57 AM, Roy Smith wrote:
> In article <mailman.6850.1392313443.18130.python-list@python.org>,
>   Ethan Furman <ethan@stoneleaf.us> wrote:
>
>> Say you have a class that represents serial ports or your computer.  You
>> should get the same object every time you ask
>> for SerialPort(2).
>
> Why?  Certainly, you should get objects which refer to the same physical
> port.  So:
>
> port_a = SerialPort(2)
> port_b = SerialPort(2)
>
> port_a.enable()
> assert port_b.is_shutdown() == False
>
> port_a.shutdown()
> assert port_b.is_shutdown() == True
>
> But, why do they have to be the same object?  Why should I care if
>
> port_a is port_b
>
> is False, as long as all operations I perform on either are reflected in
> correct state changes on the other one?

You mean use the Borg pattern instead of the Singleton pattern?  As far as I can tell they are two shades of the same 
thing.  Are there any drastic differences between the two?  Besides one having many instances that share one __dict__ 
and the other just having one instance and one __dict__?

--
~Ethan~

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


#66203

FromRoy Smith <roy@panix.com>
Date2014-02-13 14:03 -0500
Message-ID<roy-BA9C8D.14031413022014@news.panix.com>
In reply to#66202
In article <mailman.6852.1392317509.18130.python-list@python.org>,
 Ethan Furman <ethan@stoneleaf.us> wrote:

> On 02/13/2014 09:57 AM, Roy Smith wrote:
> > In article <mailman.6850.1392313443.18130.python-list@python.org>,
> >   Ethan Furman <ethan@stoneleaf.us> wrote:
> >
> >> Say you have a class that represents serial ports or your computer.  You
> >> should get the same object every time you ask
> >> for SerialPort(2).
> >
> > Why?  Certainly, you should get objects which refer to the same physical
> > port.  So:
> >
> > port_a = SerialPort(2)
> > port_b = SerialPort(2)
> >
> > port_a.enable()
> > assert port_b.is_shutdown() == False
> >
> > port_a.shutdown()
> > assert port_b.is_shutdown() == True
> >
> > But, why do they have to be the same object?  Why should I care if
> >
> > port_a is port_b
> >
> > is False, as long as all operations I perform on either are reflected in
> > correct state changes on the other one?
> 
> You mean use the Borg pattern instead of the Singleton pattern?  As far as I 
> can tell they are two shades of the same 
> thing.  Are there any drastic differences between the two?  Besides one 
> having many instances that share one __dict__ 
> and the other just having one instance and one __dict__?

I envision SerialPort being a thin layer on top of a bunch of 
OS-specific system calls to give them a pythonic interface.  Things like 
is_shutdown() and set_bit_rate() presumably turn into ioctls.  No need 
to have any state at all beyond a file descriptor.

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


#66221

FromChris Angelico <rosuav@gmail.com>
Date2014-02-14 06:50 +1100
Message-ID<mailman.6866.1392321009.18130.python-list@python.org>
In reply to#66203
On Fri, Feb 14, 2014 at 6:03 AM, Roy Smith <roy@panix.com> wrote:
> In article <mailman.6852.1392317509.18130.python-list@python.org>,
>  Ethan Furman <ethan@stoneleaf.us> wrote:
>>
>> You mean use the Borg pattern instead of the Singleton pattern?  As far as I
>> can tell they are two shades of the same
>> thing.  Are there any drastic differences between the two?  Besides one
>> having many instances that share one __dict__
>> and the other just having one instance and one __dict__?
>
> I envision SerialPort being a thin layer on top of a bunch of
> OS-specific system calls to give them a pythonic interface.  Things like
> is_shutdown() and set_bit_rate() presumably turn into ioctls.  No need
> to have any state at all beyond a file descriptor.

I'd go a bit further. The SerialPort instance would have its own
effective state: the file descriptor. Two of them can be created and
one of them closed, and the fd for that one would be closed while the
other stays open. It's then two objects dealing with a common external
facility.

ChrisA

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


#66267

FromGrant Edwards <invalid@invalid.invalid>
Date2014-02-13 22:28 +0000
Message-ID<ldjgtk$kgt$1@reader1.panix.com>
In reply to#66203
On 2014-02-13, Roy Smith <roy@panix.com> wrote:

> I envision SerialPort being a thin layer on top of a bunch of 
> OS-specific system calls to give them a pythonic interface.

Yep, that's pretty much what pyserial is

  http://pyserial.sourceforge.net/

> Things like is_shutdown() and set_bit_rate() presumably turn into
> ioctls. No need to have any state at all beyond a file descriptor.

There are OS-dependent things that it's handy to cache in the object
(e.g. a Posix port's current termios settings).  It can eliminate a
lot of ioctl() calls if the app spends a lot of time doing things like
messing with modem control lines.  The savings in ioctl() calls may
not be worth worrying about, but it's actually simpler/easier to write
that way.

OTOH, caching the termios settings it can cause breakage if two
different processes or port objects are messing with the configuration
of a single port.  People who do that are just begging for breakage
anyway, so they get no sympathy from me...

-- 
Grant Edwards               grant.b.edwards        Yow! I smell a RANCID
                                  at               CORN DOG!
                              gmail.com            

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


Page 1 of 2  [1] 2  Next page →

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


csiph-web