Define binary operations that have a domain, like divide. They have no reduce, outer or accumulate. Parameters ---------- mbfunc : function The function for which to define a masked version. Made available as ``_DomainedBinaryOperation.f``. domain : class i
| 1173 | |
| 1174 | |
| 1175 | class _DomainedBinaryOperation(_MaskedUFunc): |
| 1176 | """ |
| 1177 | Define binary operations that have a domain, like divide. |
| 1178 | |
| 1179 | They have no reduce, outer or accumulate. |
| 1180 | |
| 1181 | Parameters |
| 1182 | ---------- |
| 1183 | mbfunc : function |
| 1184 | The function for which to define a masked version. Made available |
| 1185 | as ``_DomainedBinaryOperation.f``. |
| 1186 | domain : class instance |
| 1187 | Default domain for the function. Should be one of the ``_Domain*`` |
| 1188 | classes. |
| 1189 | fillx : scalar, optional |
| 1190 | Filling value for the first argument, default is 0. |
| 1191 | filly : scalar, optional |
| 1192 | Filling value for the second argument, default is 0. |
| 1193 | |
| 1194 | """ |
| 1195 | |
| 1196 | def __init__(self, dbfunc, domain, fillx=0, filly=0): |
| 1197 | """abfunc(fillx, filly) must be defined. |
| 1198 | abfunc(x, filly) = x for all x to enable reduce. |
| 1199 | """ |
| 1200 | super().__init__(dbfunc) |
| 1201 | self.domain = domain |
| 1202 | self.fillx = fillx |
| 1203 | self.filly = filly |
| 1204 | ufunc_domain[dbfunc] = domain |
| 1205 | ufunc_fills[dbfunc] = (fillx, filly) |
| 1206 | |
| 1207 | def __call__(self, a, b, *args, **kwargs): |
| 1208 | "Execute the call behavior." |
| 1209 | # Get the data |
| 1210 | (da, db) = (getdata(a), getdata(b)) |
| 1211 | # Get the result |
| 1212 | with np.errstate(divide='ignore', invalid='ignore'): |
| 1213 | result = self.f(da, db, *args, **kwargs) |
| 1214 | # Get the mask as a combination of the source masks and invalid |
| 1215 | m = ~umath.isfinite(result) |
| 1216 | m |= getmask(a) |
| 1217 | m |= getmask(b) |
| 1218 | # Apply the domain |
| 1219 | domain = ufunc_domain.get(self.f, None) |
| 1220 | if domain is not None: |
| 1221 | m |= domain(da, db) |
| 1222 | # Take care of the scalar case first |
| 1223 | if not m.ndim: |
| 1224 | if m: |
| 1225 | return masked |
| 1226 | else: |
| 1227 | return result |
| 1228 | # When the mask is True, put back da if possible |
| 1229 | # any errors, just abort; impossible to guarantee masked values |
| 1230 | try: |
| 1231 | np.copyto(result, 0, casting='unsafe', where=m) |
| 1232 | # avoid using "*" since this may be overlaid |
no outgoing calls
no test coverage detected
searching dependent graphs…