What's better about Ruby than Python?

Jack Diederich jack at performancedrivers.com
Tue Aug 19 03:26:35 CEST 2003


On Tue, Aug 19, 2003 at 01:46:20AM +0100, Alexander Schmolck wrote:
> Gonçalo Rodrigues <op73418 at mail.telepac.pt> writes:
> 
> > On 18 Aug 2003 23:40:58 +0100, Alexander Schmolck <a.schmolck at gmx.net>
> > wrote:
> 
> > >But of course what currently happens is:
> > >
> > >'just a method'
> > >
> > 
> > And rightly so,  you have just rebinded a name. If you type
> > 
> > x.__class__
> > 
> > you get the older X. Or are you proposing that rebinding X to
> > automagically rebind the __class__ of all the X instances?
> 
> Well, yes, I propose that x.__class__ return the *new* definition of X (like
> in ruby, for example). I don't think that necessarily involves rebinding
> anything "automagical", depending on how the lookup of x.__class__ works.
> 
> Can you give my any reason why you would *not* want all instances to be
> updated on class redefinition?

Python names aren't special in any way so making names special when associated
with a class as opposed to a function or variable would make it less
intuitive for users.  Pyhon also doesn't have anonymous classes, so an odd
but perfectly OK program could be written

class Anon(Exception): pass
raise_this_later(Anon) # stores it for later

class Anon(Exception):
  def __str__(self):
    return "Slightly different exception"
raise_this_later(Anon)

Explicit is better than implicit requires that the programmer specifically
change all old 'Anon' classes into the new classes.  Writing a metaclass
to do this explicitly for you just for all the classes that might be
redefined is also OK.

# completely untested, I haven't overidden __new__ in practice so that line
# might be a bit off.

class NamesMatter(type):
  all_seen_classes = {}
  all_seen_instances = []
    
  def __init__(cls, name, bases, dict):
    """If a class name is reused rebind all the old instances to the new class"""
    if (name in NamesMatter.all_seen_classes):
      for (ob) in filter(lambda x:x.__class__ == NamesMatter.all_seen_classes[name]):
        ob.__class__ = cls
    NamesMatter.all_seen_classes[name] = cls
    def remember_obs__new__(cls, **args, **opts):
      """A custom __new__ that records instances in a central place"""
      self = object.__new__(cls)
      NamesMatter.all_seen_instances.append(self)
      return self
    setattr(cls, '__new__', classmethod(remember_obs__new__))
    return

# usage
class Anon(object): pass # a class that doesn't upgrade itself

class Upgrader(object):
  __metaclass__ = NameMatter
  """Instances of this class will be upgraded to a new class if this name
     is reused"""


-jackdied





More information about the Python-list mailing list