Skip to content

Instantly share code, notes, and snippets.

@jathanism
Created March 6, 2013 14:56
Show Gist options
  • Select an option

  • Save jathanism/5099826 to your computer and use it in GitHub Desktop.

Select an option

Save jathanism/5099826 to your computer and use it in GitHub Desktop.
Implementations of the Highlander (Singleton) and Borg (Monostate) patterns for keeping globally accessible data.
"""
highborg.py - Highlander vs. Borg.
Implementations of the Highlander (Singleton) and Borg (Monostate) patterns for
keeping globally accessible data.
New-Style Highlander credit:
http://code.activestate.com/recipes/66531-singleton-we-dont-need-no-stinkin-singleton-the-bo/#c22
New-Style Borg credit:
http://code.activestate.com/recipes/66531-singleton-we-dont-need-no-stinkin-singleton-the-bo/#c20
"""
class Highlander(object):
"""
Shares *identity* between instances (aka the "Singleton" pattern).
Only one instance can exist globally per subclass. Identity tests (``is``,
``id(foo) == id(bar)``) will return ``True``. All new instances have
``self`` replaced with the master instance.
A change to any internals affects all references to the instance.
"""
def __new__(cls, *p, **k):
if not '_instance' in cls.__dict__:
cls._instance = object.__new__(cls)
return cls._instance
def __repr__(self):
return '%s({%s})' % (self.__class__.__name__,
str(', '.join('%s : %s' % (repr(k), repr(v)) for
(k, v) in self.__dict__.iteritems())))
class NetDevices(Highlander):
def __init__(self, name, *args, **kwargs):
super(NetDevices, self).__init__(*args, **kwargs)
self.name = name
class Borg(object):
"""
Shares *state* between instances (aka the "Monostate" pattern).
Each instance shares the same internal state per subclass. Identity tests
will return ``False``. All new instances have their dict referencing the
state dict in the class object.
A change to any internals affects all instances.
"""
_state = {}
def __new__(cls, *p, **k):
self = object.__new__(cls, *p, **k)
self.__dict__ = cls._state
return self
def __repr__(self):
return '%s({%s})' % (self.__class__.__name__,
str(', '.join('%s: %s' % (repr(k), repr(v)) for
(k, v) in self.__dict__.iteritems())))
class BorgDevices(Borg):
def __init__(self, *args, **kwargs):
data = args[0] if args else kwargs.get('data', {})
self.__dict__.update(data)
super(BorgDevices, self).__init__(*args, **kwargs)
if __name__ == '__main__':
print 'Highlander tests...'
print '=' * 10
nd = NetDevices('foo')
print 'nd.name', nd.name
fd = NetDevices('boo')
print 'fd.name', fd.name
print 'nd.name', nd.name
print
print 'Borg tests...'
print '=' * 10
bd = BorgDevices({'foo': 'bar', 'spam': 'eggs'})
print 'bd.foo', bd.foo
bd2 = BorgDevices()
print 'bd2.foo', bd2.foo
bd3 = BorgDevices({'bacon': 'win', 'apples': 'oranges'})
print 'bd3.bacon', bd3.bacon
print 'bd.bacon', bd.bacon
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment