def ScaleTransform_img_gt(imgs, *args) -> Tuple[Any, Any]: """ Given the input array, return the expected output array and shape after applying the resize transformation. Args: imgs (array): image(s) array before the transform. args (list): list of arguments. Details can be found in test case. Returns: img (array): expected output array after apply the transformation. None means does not have expected output array for sanity check. (list): expected shape of the output array. None means does not have expected output shape for sanity check. """ h, w, new_h, new_w, interp = args float_tensor = to_float_tensor(imgs) if interp == "nearest": if float_tensor.dim() == 3: float_tensor = torch._C._nn.upsample_nearest1d( float_tensor, (new_h, new_w)) elif float_tensor.dim() == 4: float_tensor = torch._C._nn.upsample_nearest2d( float_tensor, (new_h, new_w)) elif float_tensor.dim() == 5: float_tensor = torch._C._nn.upsample_nearest3d( float_tensor, (new_h, new_w)) else: return None, None elif interp == "bilinear": if float_tensor.dim() == 4: float_tensor = torch._C._nn.upsample_bilinear2d( float_tensor, (new_h, new_w), False) else: return None, None numpy_tensor = to_numpy(float_tensor, imgs.shape, imgs.dtype) return numpy_tensor, numpy_tensor.shape
def apply_image(self, img: np.ndarray, interp: str = None) -> np.ndarray: """ Resize the image(s). Args: img (ndarray): of shape NxHxWxC, or HxWxC or HxW. The array can be of type uint8 in range [0, 255], or floating point in range [0, 1] or [0, 255]. interp (str): interpolation methods. Options includes `nearest`, `linear` (3D-only), `bilinear`, `bicubic` (4D-only), and `area`. Details can be found in: https://pytorch.org/docs/stable/nn.functional.html Returns: ndarray: resized image(s). """ if len(img.shape) == 4: h, w = img.shape[1:3] elif len(img.shape) in (2, 3): h, w = img.shape[:2] else: raise ("Unsupported input with shape of {}".format(img.shape)) assert (self.h == h and self.w == w), "Input size mismatch h w {}:{} -> {}:{}".format( self.h, self.w, h, w) interp_method = interp if interp is not None else self.interp # Option of align_corners is only supported for linear, bilinear, # and bicubic. if interp_method in ["linear", "bilinear", "bicubic"]: align_corners = False else: align_corners = None # note: this is quite slow for int8 images because torch does not # support it https://github.com/pytorch/pytorch/issues/5580 float_tensor = torch.nn.functional.interpolate( to_float_tensor(img), size=(self.new_h, self.new_w), mode=interp_method, align_corners=align_corners, ) return to_numpy(float_tensor, img.shape, img.dtype)
def test_convert(self) -> None: N, C, H, W = 4, 64, 14, 14 np.random.seed(0) array_HW: np.ndarray = np.random.rand(H, W) array_HWC: np.ndarray = np.random.rand(H, W, C) array_NHWC: np.ndarray = np.random.rand(N, H, W, C) arrays = [ array_HW, (array_HW * 255).astype(np.uint8), array_HWC, (array_HWC * 255).astype(np.uint8), array_NHWC, (array_NHWC * 255).astype(np.uint8), ] for array in arrays: converted_tensor = to_float_tensor(array) converted_array = to_numpy(converted_tensor, array.shape, array.dtype) self.assertTrue(np.allclose(array, converted_array))
def ScaleTransform_seg_gt(seg, *args) -> Tuple[np.ndarray, list]: """ Given the input segmentation, return the expected output array and shape after applying the blend transformation. Args: seg (array): segmentation before the transform. args (list): list of arguments. Details can be found in test case. Returns: seg (array): expected output segmentation after apply the transformation. (list): expected shape of the output array. """ h, w, new_h, new_w = args float_tensor = torch.nn.functional.interpolate( to_float_tensor(seg), size=(new_h, new_w), mode="nearest", align_corners=None, ) numpy_tensor = to_numpy(float_tensor, seg.shape, seg.dtype) return numpy_tensor, numpy_tensor.shape
def apply_image(self, img: np.ndarray, interp: str = None) -> np.ndarray: """ Apply grid sampling on the image(s). Args: img (ndarray): of shape NxHxWxC, or HxWxC or HxW. The array can be of type uint8 in range [0, 255], or floating point in range [0, 1] or [0, 255]. interp (str): interpolation methods. Options include `nearest` and `bilinear`. Returns: ndarray: grid sampled image(s). """ interp_method = interp if interp is not None else self.interp float_tensor = torch.nn.functional.grid_sample( to_float_tensor(img), # NxHxWxC -> NxCxHxW. torch.from_numpy(self.grid), mode=interp_method, padding_mode="border", align_corners=False, ) return to_numpy(float_tensor, img.shape, img.dtype)