Passed
Push — master ( af9889...f446f0 )
by Max
01:14
created

structured_data._adt.prewritten_methods   A

Complexity

Total Complexity 28

Size/Duplication

Total Lines 114
Duplicated Lines 0 %

Importance

Changes 0
Metric Value
wmc 28
eloc 81
dl 0
loc 114
rs 10
c 0
b 0
f 0

13 Methods

Rating   Name   Duplication   Size   Complexity  
A PrewrittenSumMethods.__lt__() 0 9 3
A PrewrittenProductMethods.__le__() 0 4 2
A CommonPrewrittenMethods.__ne__() 0 4 2
A PrewrittenProductMethods.__ge__() 0 4 2
A PrewrittenProductMethods.__gt__() 0 4 2
A CommonPrewrittenMethods.__repr__() 0 3 1
A PrewrittenProductMethods.__lt__() 0 4 2
A PrewrittenSumMethods.__ge__() 0 9 3
A CommonPrewrittenMethods.__eq__() 0 4 2
A CommonPrewrittenMethods.__hash__() 0 2 1
A PrewrittenSumMethods.__gt__() 0 9 3
A PrewrittenSumMethods.__init_subclass__() 0 2 1
A PrewrittenSumMethods.__le__() 0 9 3

1 Function

Rating   Name   Duplication   Size   Complexity  
A sum_base() 0 3 1
1
"""Methods to be added to ADT classes."""
2
3
import typing
4
import weakref
5
6
from .._unpack import unpack
7
from .constructor import ADT_BASES
8
9
10
def sum_base(obj):
11
    """Return the immediate base class of the type of a ``Sum`` instance."""
12
    return ADT_BASES.get(obj.__class__)
13
14
15
SUBCLASS_ORDER: typing.MutableMapping[
16
    type, typing.Tuple[type, ...]
17
] = weakref.WeakKeyDictionary()
18
19
20
class CommonPrewrittenMethods:
21
    """Methods to slot into various modified classes."""
22
23
    def __repr__(self):
24
        return "{}({})".format(
25
            self.__class__.__qualname__, ", ".join(repr(item) for item in unpack(self))
26
        )
27
28
    def __eq__(self, other):
29
        if other.__class__ is self.__class__:
30
            return unpack(self) == unpack(other)
31
        return False
32
33
    def __ne__(self, other):
34
        if other.__class__ is self.__class__:
35
            return unpack(self) != unpack(other)
36
        return True
37
38
    def __hash__(self):
39
        return hash(unpack(self))
40
41
42
class PrewrittenProductMethods(CommonPrewrittenMethods):
43
    """Methods for subclasses of ``structured_data.adt.Product``."""
44
45
    def __lt__(self, other):
46
        if other.__class__ is self.__class__:
47
            return unpack(self) < unpack(other)
48
        raise TypeError
49
50
    def __le__(self, other):
51
        if other.__class__ is self.__class__:
52
            return unpack(self) <= unpack(other)
53
        raise TypeError
54
55
    def __gt__(self, other):
56
        if other.__class__ is self.__class__:
57
            return unpack(self) > unpack(other)
58
        raise TypeError
59
60
    def __ge__(self, other):
61
        if other.__class__ is self.__class__:
62
            return unpack(self) >= unpack(other)
63
        raise TypeError
64
65
66
class PrewrittenSumMethods(CommonPrewrittenMethods):
67
    """Methods for subclasses of ``structured_data.adt.Sum``."""
68
69
    def __init_subclass__(cls, **kwargs):
70
        raise TypeError(f"Cannot further subclass the class {cls.__name__}")
71
72
    def __lt__(self, other):
73
        if other.__class__ is self.__class__:
74
            return unpack(self) < unpack(other)
75
        if sum_base(other) is sum_base(self):
76
            order = SUBCLASS_ORDER.get(sum_base(self))
77
            self_index = order.index(self.__class__)
78
            other_index = order.index(other.__class__)
79
            return self_index < other_index
80
        raise TypeError
81
82
    def __le__(self, other):
83
        if other.__class__ is self.__class__:
84
            return unpack(self) <= unpack(other)
85
        if sum_base(other) is sum_base(self):
86
            order = SUBCLASS_ORDER.get(sum_base(self))
87
            self_index = order.index(self.__class__)
88
            other_index = order.index(other.__class__)
89
            return self_index <= other_index
90
        raise TypeError
91
92
    def __gt__(self, other):
93
        if other.__class__ is self.__class__:
94
            return unpack(self) > unpack(other)
95
        if sum_base(other) is sum_base(self):
96
            order = SUBCLASS_ORDER.get(sum_base(self))
97
            self_index = order.index(self.__class__)
98
            other_index = order.index(other.__class__)
99
            return self_index > other_index
100
        raise TypeError
101
102
    def __ge__(self, other):
103
        if other.__class__ is self.__class__:
104
            return unpack(self) >= unpack(other)
105
        if sum_base(other) is sum_base(self):
106
            order = SUBCLASS_ORDER.get(sum_base(self))
107
            self_index = order.index(self.__class__)
108
            other_index = order.index(other.__class__)
109
            return self_index >= other_index
110
        raise TypeError
111
112
113
__all__ = ["PrewrittenProductMethods", "PrewrittenSumMethods"]
114