diff options
Diffstat (limited to 'Demo/metaclasses/Enum.py')
-rw-r--r-- | Demo/metaclasses/Enum.py | 168 |
1 files changed, 0 insertions, 168 deletions
diff --git a/Demo/metaclasses/Enum.py b/Demo/metaclasses/Enum.py deleted file mode 100644 index eb52d79..0000000 --- a/Demo/metaclasses/Enum.py +++ /dev/null @@ -1,168 +0,0 @@ -"""Enumeration metaclass. - -XXX This is very much a work in progress. - -""" - -import string - -class EnumMetaClass: - """Metaclass for enumeration. - - To define your own enumeration, do something like - - class Color(Enum): - red = 1 - green = 2 - blue = 3 - - Now, Color.red, Color.green and Color.blue behave totally - different: they are enumerated values, not integers. - - Enumerations cannot be instantiated; however they can be - subclassed. - - """ - - def __init__(self, name, bases, dict): - """Constructor -- create an enumeration. - - Called at the end of the class statement. The arguments are - the name of the new class, a tuple containing the base - classes, and a dictionary containing everything that was - entered in the class' namespace during execution of the class - statement. In the above example, it would be {'red': 1, - 'green': 2, 'blue': 3}. - - """ - for base in bases: - if base.__class__ is not EnumMetaClass: - raise TypeError("Enumeration base class must be enumeration") - bases = [x for x in bases if x is not Enum] - self.__name__ = name - self.__bases__ = bases - self.__dict = {} - for key, value in dict.items(): - self.__dict[key] = EnumInstance(name, key, value) - - def __getattr__(self, name): - """Return an enumeration value. - - For example, Color.red returns the value corresponding to red. - - XXX Perhaps the values should be created in the constructor? - - This looks in the class dictionary and if it is not found - there asks the base classes. - - The special attribute __members__ returns the list of names - defined in this class (it does not merge in the names defined - in base classes). - - """ - if name == '__members__': - return list(self.__dict.keys()) - - try: - return self.__dict[name] - except KeyError: - for base in self.__bases__: - try: - return getattr(base, name) - except AttributeError: - continue - - raise AttributeError(name) - - def __repr__(self): - s = self.__name__ - if self.__bases__: - s = s + '(' + string.join([x.__name__ for x in self.__bases__], ", ") + ')' - if self.__dict: - list = [] - for key, value in self.__dict.items(): - list.append("%s: %s" % (key, int(value))) - s = "%s: {%s}" % (s, string.join(list, ", ")) - return s - - -class EnumInstance: - """Class to represent an enumeration value. - - EnumInstance('Color', 'red', 12) prints as 'Color.red' and behaves - like the integer 12 when compared, but doesn't support arithmetic. - - XXX Should it record the actual enumeration rather than just its - name? - - """ - - def __init__(self, classname, enumname, value): - self.__classname = classname - self.__enumname = enumname - self.__value = value - - def __int__(self): - return self.__value - - def __repr__(self): - return "EnumInstance(%r, %r, %r)" % (self.__classname, - self.__enumname, - self.__value) - - def __str__(self): - return "%s.%s" % (self.__classname, self.__enumname) - - def __cmp__(self, other): - return cmp(self.__value, int(other)) - - -# Create the base class for enumerations. -# It is an empty enumeration. -Enum = EnumMetaClass("Enum", (), {}) - - -def _test(): - - class Color(Enum): - red = 1 - green = 2 - blue = 3 - - print(Color.red) - print(dir(Color)) - - print(Color.red == Color.red) - print(Color.red == Color.blue) - print(Color.red == 1) - print(Color.red == 2) - - class ExtendedColor(Color): - white = 0 - orange = 4 - yellow = 5 - purple = 6 - black = 7 - - print(ExtendedColor.orange) - print(ExtendedColor.red) - - print(Color.red == ExtendedColor.red) - - class OtherColor(Enum): - white = 4 - blue = 5 - - class MergedColor(Color, OtherColor): - pass - - print(MergedColor.red) - print(MergedColor.white) - - print(Color) - print(ExtendedColor) - print(OtherColor) - print(MergedColor) - -if __name__ == '__main__': - _test() |