Skip to content

Commit

Permalink
Merge branch 'dev' into 6007-pil-reader
Browse files Browse the repository at this point in the history
  • Loading branch information
wyli authored Feb 15, 2023
2 parents e9acacf + f4902b2 commit 7460aa4
Show file tree
Hide file tree
Showing 18 changed files with 123 additions and 111 deletions.
2 changes: 1 addition & 1 deletion .github/dependabot.yml
Original file line number Diff line number Diff line change
Expand Up @@ -7,4 +7,4 @@ updates:
directory: "/"
schedule:
# Check for updates to GitHub Actions every week
interval: "weekly"
interval: "monthly"
2 changes: 1 addition & 1 deletion .github/workflows/blossom-ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v2
uses: actions/checkout@v3
with:
repository: ${{ fromJson(needs.Authorization.outputs.args).repo }}
ref: ${{ fromJson(needs.Authorization.outputs.args).ref }}
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/chatops.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: dispatch
uses: peter-evans/slash-command-dispatch@v1.2.0
uses: peter-evans/slash-command-dispatch@v3.0.1
with:
token: ${{ secrets.PR_MAINTAIN }}
reaction-token: ${{ secrets.GITHUB_TOKEN }}
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/conda.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ jobs:
steps:
- if: runner.os == 'windows'
name: Config pagefile (Windows only)
uses: al-cheb/configure-pagefile-action@v1.2
uses: al-cheb/configure-pagefile-action@v1.3
with:
minimum-size: 8
maximum-size: 16
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/docker.yml
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ jobs:
python setup.py build
cat build/lib/monai/_version.py
- name: Upload version
uses: actions/upload-artifact@v2
uses: actions/upload-artifact@v3
with:
name: _version.py
path: build/lib/monai/_version.py
Expand All @@ -55,7 +55,7 @@ jobs:
with:
ref: dev
- name: Download version
uses: actions/download-artifact@v2
uses: actions/download-artifact@v3
with:
name: _version.py
- name: Install Latest Docker
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/integration.yml
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ jobs:
if pgrep python; then pkill python; fi
shell: bash
- name: Add reaction
uses: peter-evans/create-or-update-comment@v1
uses: peter-evans/create-or-update-comment@v2
if: github.event.pull_request.number != ''
with:
token: ${{ secrets.PR_MAINTAIN }}
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/pythonapp.yml
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ jobs:
steps:
- if: runner.os == 'windows'
name: Config pagefile (Windows only)
uses: al-cheb/configure-pagefile-action@v1.2
uses: al-cheb/configure-pagefile-action@v1.3
with:
minimum-size: 8
maximum-size: 16
Expand Down
6 changes: 3 additions & 3 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ jobs:

- if: matrix.python-version == '3.8' && startsWith(github.ref, 'refs/tags/')
name: Upload artifacts
uses: actions/upload-artifact@v1
uses: actions/upload-artifact@v3
with:
name: dist
path: dist/
Expand Down Expand Up @@ -105,7 +105,7 @@ jobs:
python setup.py build
cat build/lib/monai/_version.py
- name: Upload version
uses: actions/upload-artifact@v2
uses: actions/upload-artifact@v3
with:
name: _version.py
path: build/lib/monai/_version.py
Expand All @@ -122,7 +122,7 @@ jobs:
steps:
- uses: actions/checkout@v3
- name: Download version
uses: actions/download-artifact@v2
uses: actions/download-artifact@v3
with:
name: _version.py
- name: Set tag
Expand Down
14 changes: 2 additions & 12 deletions monai/transforms/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -453,18 +453,8 @@
ZoomD,
ZoomDict,
)
from .transform import (
LazyTrait,
LazyTransform,
MapTransform,
MultiSampleTrait,
Randomizable,
RandomizableTrait,
RandomizableTransform,
ThreadUnsafe,
Transform,
apply_transform,
)
from .traits import LazyTrait, MultiSampleTrait, RandomizableTrait, ThreadUnsafe
from .transform import LazyTransform, MapTransform, Randomizable, RandomizableTransform, Transform, apply_transform
from .utility.array import (
AddChannel,
AddCoordinateChannels,
Expand Down
9 changes: 5 additions & 4 deletions monai/transforms/croppad/array.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
from monai.data.meta_tensor import MetaTensor
from monai.data.utils import get_random_patch, get_valid_patch_size
from monai.transforms.inverse import InvertibleTransform, TraceableTransform
from monai.transforms.traits import MultiSampleTrait
from monai.transforms.transform import Randomizable, Transform
from monai.transforms.utils import (
compute_divisible_spatial_size,
Expand Down Expand Up @@ -683,7 +684,7 @@ def __call__(self, img: torch.Tensor, randomize: bool = True) -> torch.Tensor:
return super().__call__(img=img, randomize=randomize)


class RandSpatialCropSamples(Randomizable, TraceableTransform):
class RandSpatialCropSamples(Randomizable, TraceableTransform, MultiSampleTrait):
"""
Crop image with random size or specific size ROI to generate a list of N samples.
It can crop at a random position as center or at the image center. And allows to set
Expand Down Expand Up @@ -893,7 +894,7 @@ def inverse(self, img: MetaTensor) -> MetaTensor:
return super().inverse(inv)


class RandWeightedCrop(Randomizable, TraceableTransform):
class RandWeightedCrop(Randomizable, TraceableTransform, MultiSampleTrait):
"""
Samples a list of `num_samples` image patches according to the provided `weight_map`.
Expand Down Expand Up @@ -958,7 +959,7 @@ def __call__(
return results


class RandCropByPosNegLabel(Randomizable, TraceableTransform):
class RandCropByPosNegLabel(Randomizable, TraceableTransform, MultiSampleTrait):
"""
Crop random fixed sized regions with the center being a foreground or background voxel
based on the Pos Neg Ratio.
Expand Down Expand Up @@ -1118,7 +1119,7 @@ def __call__(
return results


class RandCropByLabelClasses(Randomizable, TraceableTransform):
class RandCropByLabelClasses(Randomizable, TraceableTransform, MultiSampleTrait):
"""
Crop random fixed sized regions with the center being a class based on the specified ratios of every class.
The label data can be One-Hot format array or Argmax data. And will return a list of arrays for all the
Expand Down
9 changes: 5 additions & 4 deletions monai/transforms/croppad/dictionary.py
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@
SpatialPad,
)
from monai.transforms.inverse import InvertibleTransform
from monai.transforms.traits import MultiSampleTrait
from monai.transforms.transform import MapTransform, Randomizable
from monai.transforms.utils import is_positive
from monai.utils import MAX_SEED, Method, PytorchPadMode, deprecated_arg_default, ensure_tuple_rep
Expand Down Expand Up @@ -528,7 +529,7 @@ def __init__(
super().__init__(keys, cropper=cropper, allow_missing_keys=allow_missing_keys)


class RandSpatialCropSamplesd(Randomizable, MapTransform):
class RandSpatialCropSamplesd(Randomizable, MapTransform, MultiSampleTrait):
"""
Dictionary-based version :py:class:`monai.transforms.RandSpatialCropSamples`.
Crop image with random size or specific size ROI to generate a list of N samples.
Expand Down Expand Up @@ -682,7 +683,7 @@ def __call__(self, data: Mapping[Hashable, torch.Tensor]) -> dict[Hashable, torc
return d


class RandWeightedCropd(Randomizable, MapTransform):
class RandWeightedCropd(Randomizable, MapTransform, MultiSampleTrait):
"""
Samples a list of `num_samples` image patches according to the provided `weight_map`.
Expand Down Expand Up @@ -739,7 +740,7 @@ def __call__(self, data: Mapping[Hashable, torch.Tensor]) -> list[dict[Hashable,
return ret


class RandCropByPosNegLabeld(Randomizable, MapTransform):
class RandCropByPosNegLabeld(Randomizable, MapTransform, MultiSampleTrait):
"""
Dictionary-based version :py:class:`monai.transforms.RandCropByPosNegLabel`.
Crop random fixed sized regions with the center being a foreground or background voxel
Expand Down Expand Up @@ -860,7 +861,7 @@ def __call__(self, data: Mapping[Hashable, torch.Tensor]) -> list[dict[Hashable,
return ret


class RandCropByLabelClassesd(Randomizable, MapTransform):
class RandCropByLabelClassesd(Randomizable, MapTransform, MultiSampleTrait):
"""
Dictionary-based version :py:class:`monai.transforms.RandCropByLabelClasses`.
Crop random fixed sized regions with the center being a class based on the specified ratios of every class.
Expand Down
3 changes: 2 additions & 1 deletion monai/transforms/nvtx.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,8 @@

from __future__ import annotations

from monai.transforms.transform import RandomizableTrait, Transform
from monai.transforms.traits import RandomizableTrait
from monai.transforms.transform import Transform
from monai.utils import optional_import

_nvtx, _ = optional_import("torch._C._nvtx", descriptor="NVTX is not installed. Are you sure you have a CUDA build?")
Expand Down
7 changes: 4 additions & 3 deletions monai/transforms/spatial/array.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
from monai.transforms.croppad.array import CenterSpatialCrop, ResizeWithPadOrCrop
from monai.transforms.intensity.array import GaussianSmooth
from monai.transforms.inverse import InvertibleTransform
from monai.transforms.traits import MultiSampleTrait
from monai.transforms.transform import Randomizable, RandomizableTransform, Transform
from monai.transforms.utils import (
convert_pad_mode,
Expand Down Expand Up @@ -3045,7 +3046,7 @@ def __call__(
return self.grid_distortion(img, distort_steps=self.distort_steps, mode=mode, padding_mode=padding_mode)


class GridSplit(Transform):
class GridSplit(Transform, MultiSampleTrait):
"""
Split the image into patches based on the provided grid in 2D.
Expand Down Expand Up @@ -3130,7 +3131,7 @@ def _get_params(self, image_size: Sequence[int] | np.ndarray, size: Sequence[int
return size, steps


class GridPatch(Transform):
class GridPatch(Transform, MultiSampleTrait):
"""
Extract all the patches sweeping the entire image in a row-major sliding-window manner with possible overlaps.
It can sort the patches and return all or a subset of them.
Expand Down Expand Up @@ -3257,7 +3258,7 @@ def __call__(self, array: NdarrayOrTensor):
return output


class RandGridPatch(GridPatch, RandomizableTransform):
class RandGridPatch(GridPatch, RandomizableTransform, MultiSampleTrait):
"""
Extract all the patches sweeping the entire image in a row-major sliding-window manner with possible overlaps,
and with random offset for the minimal corner of the image, (0,0) for 2D and (0,0,0) for 3D.
Expand Down
7 changes: 4 additions & 3 deletions monai/transforms/spatial/dictionary.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@
SpatialResample,
Zoom,
)
from monai.transforms.traits import MultiSampleTrait
from monai.transforms.transform import MapTransform, RandomizableTransform
from monai.transforms.utils import create_grid
from monai.utils import (
Expand Down Expand Up @@ -1779,7 +1780,7 @@ def __call__(self, data: Mapping[Hashable, torch.Tensor]) -> dict[Hashable, torc
return d


class GridSplitd(MapTransform):
class GridSplitd(MapTransform, MultiSampleTrait):
"""
Split the image into patches based on the provided grid in 2D.
Expand Down Expand Up @@ -1820,7 +1821,7 @@ def __call__(self, data: Mapping[Hashable, NdarrayOrTensor]) -> list[dict[Hashab
return output


class GridPatchd(MapTransform):
class GridPatchd(MapTransform, MultiSampleTrait):
"""
Extract all the patches sweeping the entire image in a row-major sliding-window manner with possible overlaps.
It can sort the patches and return all or a subset of them.
Expand Down Expand Up @@ -1884,7 +1885,7 @@ def __call__(self, data: Mapping[Hashable, NdarrayOrTensor]) -> dict[Hashable, N
return d


class RandGridPatchd(RandomizableTransform, MapTransform):
class RandGridPatchd(RandomizableTransform, MapTransform, MultiSampleTrait):
"""
Extract all the patches sweeping the entire image in a row-major sliding-window manner with possible overlaps,
and with random offset for the minimal corner of the image, (0,0) for 2D and (0,0,0) for 3D.
Expand Down
80 changes: 80 additions & 0 deletions monai/transforms/traits.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
# Copyright (c) MONAI Consortium
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
# http://www.apache.org/licenses/LICENSE-2.0
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""
A collection of generic traits for MONAI transforms.
"""

from __future__ import annotations

__all__ = ["LazyTrait", "RandomizableTrait", "MultiSampleTrait", "ThreadUnsafe"]


class LazyTrait:
"""
An interface to indicate that the transform has the capability to execute using
MONAI's lazy resampling feature. In order to do this, the implementing class needs
to be able to describe its operation as an affine matrix or grid with accompanying metadata.
This interface can be extended from by people adapting transforms to the MONAI framework as
well as by implementors of MONAI transforms.
"""

@property
def lazy_evaluation(self):
"""
Get whether lazy_evaluation is enabled for this transform instance.
Returns:
True if the transform is operating in a lazy fashion, False if not.
"""
raise NotImplementedError()

@lazy_evaluation.setter
def lazy_evaluation(self, enabled: bool):
"""
Set whether lazy_evaluation is enabled for this transform instance.
Args:
enabled: True if the transform should operate in a lazy fashion, False if not.
"""
raise NotImplementedError()


class RandomizableTrait:
"""
An interface to indicate that the transform has the capability to perform
randomized transforms to the data that it is called upon. This interface
can be extended from by people adapting transforms to the MONAI framework as well as by
implementors of MONAI transforms.
"""

pass


class MultiSampleTrait:
"""
An interface to indicate that the transform has the capability to return multiple samples
given an input, such as when performing random crops of a sample. This interface can be
extended from by people adapting transforms to the MONAI framework as well as by implementors
of MONAI transforms.
"""

pass


class ThreadUnsafe:
"""
A class to denote that the transform will mutate its member variables,
when being applied. Transforms inheriting this class should be used
cautiously in a multi-thread context.
This type is typically used by :py:class:`monai.data.CacheDataset` and
its extensions, where the transform cache is built with multiple threads.
"""

pass
Loading

0 comments on commit 7460aa4

Please sign in to comment.