| Total Complexity | 15 |
| Total Lines | 76 |
| Duplicated Lines | 0 % |
| Changes | 0 | ||
| 1 | import keyword |
||
| 2 | |||
| 3 | DISCARD = object() |
||
| 4 | |||
| 5 | |||
| 6 | class Pattern(tuple): |
||
| 7 | """A matcher that binds a value to a name.""" |
||
| 8 | |||
| 9 | __slots__ = () |
||
| 10 | |||
| 11 | def __new__(cls, name: str): |
||
| 12 | if name == '_': |
||
| 13 | return DISCARD |
||
| 14 | if not name.isidentifier(): |
||
| 15 | raise ValueError |
||
| 16 | if keyword.iskeyword(name): |
||
| 17 | raise ValueError |
||
| 18 | return super().__new__(cls, (name,)) |
||
| 19 | |||
| 20 | @property |
||
| 21 | def name(self): |
||
| 22 | """Return the name of the matcher.""" |
||
| 23 | return self[0] |
||
| 24 | |||
| 25 | def __matmul__(self, other): |
||
| 26 | return AsPattern(self, other) |
||
| 27 | |||
| 28 | |||
| 29 | class AsPattern(tuple): |
||
| 30 | """A matcher that contains further bindings.""" |
||
| 31 | |||
| 32 | __slots__ = () |
||
| 33 | |||
| 34 | def __new__(cls, matcher: Pattern, match): |
||
| 35 | if match is DISCARD: |
||
| 36 | return matcher |
||
| 37 | return super().__new__(cls, (matcher, match)) |
||
| 38 | |||
| 39 | @property |
||
| 40 | def matcher(self): |
||
| 41 | """Return the left-hand-side of the as-match.""" |
||
| 42 | return self[0] |
||
| 43 | |||
| 44 | @property |
||
| 45 | def match(self): |
||
| 46 | """Return the right-hand-side of the as-match.""" |
||
| 47 | return self[1] |
||
| 48 | |||
| 49 | |||
| 50 | class AttrPattern(tuple): |
||
| 51 | |||
| 52 | __slots__ = () |
||
| 53 | |||
| 54 | def __new__(cls, match_dict): |
||
| 55 | return super().__new__(cls, (tuple(match_dict.items()),)) |
||
| 56 | |||
| 57 | @property |
||
| 58 | def match_dict(self): |
||
| 59 | return self[0] |
||
| 60 | |||
| 61 | |||
| 62 | class DictPattern(tuple): |
||
| 63 | |||
| 64 | __slots__ = () |
||
| 65 | |||
| 66 | def __new__(cls, match_dict, *, exhaustive=False): |
||
| 67 | return super().__new__(cls, (tuple(match_dict.items()), exhaustive)) |
||
| 68 | |||
| 69 | @property |
||
| 70 | def match_dict(self): |
||
| 71 | return self[0] |
||
| 72 | |||
| 73 | @property |
||
| 74 | def exhaustive(self): |
||
| 75 | return self[1] |
||
| 76 |