3 from abc import ABC, abstractmethod
4 from typing import Any, Generic, TypeVar
9 class DeferredOperand(ABC, Generic[T]):
10 """A wrapper around an operand whose value is deferred until it is
11 needed. See subclass SmartFuture for an example usage.
15 def _resolve(self) -> T:
19 def resolve(x: Any) -> Any:
20 while isinstance(x, DeferredOperand):
24 def __lt__(self, other: Any) -> bool:
25 return DeferredOperand.resolve(self) < DeferredOperand.resolve(other)
27 def __le__(self, other: Any) -> bool:
28 return DeferredOperand.resolve(self) <= DeferredOperand.resolve(other)
30 def __eq__(self, other: Any) -> bool:
31 return DeferredOperand.resolve(self) == DeferredOperand.resolve(other)
33 def __ne__(self, other: Any) -> bool:
34 return DeferredOperand.resolve(self) != DeferredOperand.resolve(other)
36 def __gt__(self, other: Any) -> bool:
37 return DeferredOperand.resolve(self) > DeferredOperand.resolve(other)
39 def __ge__(self, other: Any) -> bool:
40 return DeferredOperand.resolve(self) >= DeferredOperand.resolve(other)
42 def __not__(self) -> bool:
43 return not DeferredOperand.resolve(self)
45 def bool(self) -> bool:
46 return DeferredOperand.resolve(self)
48 def __add__(self, other: Any) -> T:
49 return DeferredOperand.resolve(self) + DeferredOperand.resolve(other)
51 def __iadd__(self, other: Any) -> T:
52 return DeferredOperand.resolve(self) + DeferredOperand.resolve(other)
54 def __radd__(self, other: Any) -> T:
55 return DeferredOperand.resolve(self) + DeferredOperand.resolve(other)
57 def __sub__(self, other: Any) -> T:
58 return DeferredOperand.resolve(self) - DeferredOperand.resolve(other)
60 def __mul__(self, other: Any) -> T:
61 return DeferredOperand.resolve(self) * DeferredOperand.resolve(other)
63 def __pow__(self, other: Any) -> T:
64 return DeferredOperand.resolve(self) ** DeferredOperand.resolve(other)
66 def __truediv__(self, other: Any) -> Any:
67 return DeferredOperand.resolve(self) / DeferredOperand.resolve(other)
69 def __floordiv__(self, other: Any) -> T:
70 return DeferredOperand.resolve(self) // DeferredOperand.resolve(other)
72 def __contains__(self, other):
73 return DeferredOperand.resolve(other) in DeferredOperand.resolve(self)
75 def and_(self, other):
76 return DeferredOperand.resolve(self) & DeferredOperand.resolve(other)
79 return DeferredOperand.resolve(self) & DeferredOperand.resolve(other)
82 return DeferredOperand.resolve(self) & DeferredOperand.resolve(other)
85 return ~(DeferredOperand.resolve(self))
88 return DeferredOperand.resolve(self) is DeferredOperand.resolve(other)
90 def is_not(self, other):
91 return DeferredOperand.resolve(self) is not DeferredOperand.resolve(other)
94 return abs(DeferredOperand.resolve(self))
96 def setitem(self, k, v):
97 DeferredOperand.resolve(self)[DeferredOperand.resolve(k)] = v
100 del DeferredOperand.resolve(self)[DeferredOperand.resolve(k)]
102 def getitem(self, k):
103 return DeferredOperand.resolve(self)[DeferredOperand.resolve(k)]
105 def lshift(self, other):
106 return DeferredOperand.resolve(self) << DeferredOperand.resolve(other)
108 def rshift(self, other):
109 return DeferredOperand.resolve(self) >> DeferredOperand.resolve(other)
111 def mod(self, other):
112 return DeferredOperand.resolve(self) % DeferredOperand.resolve(other)
114 def matmul(self, other):
115 return DeferredOperand.resolve(self) @ DeferredOperand.resolve(other)
118 return -(DeferredOperand.resolve(self))
121 return +(DeferredOperand.resolve(self))
124 return DeferredOperand.resolve(self)
127 return DeferredOperand.resolve(self).__hash__()
130 return DeferredOperand.resolve(self)()
133 return DeferredOperand.resolve(self).__iter__()
135 def __repr__(self) -> str:
136 return DeferredOperand.resolve(self).__repr__()
138 def __bytes__(self) -> bytes:
139 return DeferredOperand.resolve(self).__bytes__()
141 def __int__(self) -> int:
142 return int(DeferredOperand.resolve(self))
144 def __float__(self) -> float:
145 return float(DeferredOperand.resolve(self))
147 def __getattr__(self, method_name):
148 def method(*args, **kwargs):
149 return getattr(DeferredOperand.resolve(self), method_name)(