diff --git a/tests/apps/detection/networks/test_retinanet.py b/tests/apps/detection/networks/test_retinanet.py index 240fd3a9e2..f30a2cf002 100644 --- a/tests/apps/detection/networks/test_retinanet.py +++ b/tests/apps/detection/networks/test_retinanet.py @@ -20,7 +20,7 @@ from monai.networks import eval_mode from monai.networks.nets import resnet10, resnet18, resnet34, resnet50, resnet101, resnet152, resnet200 from monai.utils import ensure_tuple, optional_import -from tests.test_utils import SkipIfBeforePyTorchVersion, skip_if_quick, test_onnx_save, test_script_save +from tests.test_utils import SkipIfBeforePyTorchVersion, dict_product, skip_if_quick, test_onnx_save, test_script_save _, has_torchvision = optional_import("torchvision") @@ -86,15 +86,23 @@ (2, 1, 32, 64), ] +# Create all test case combinations using dict_product +CASE_LIST = [TEST_CASE_1, TEST_CASE_2, TEST_CASE_3, TEST_CASE_2_A, TEST_CASE_3_A] +MODEL_LIST = [resnet10, resnet18, resnet34, resnet50, resnet101, resnet152, resnet200] + TEST_CASES = [] -for case in [TEST_CASE_1, TEST_CASE_2, TEST_CASE_3, TEST_CASE_2_A, TEST_CASE_3_A]: - for model in [resnet10, resnet18, resnet34, resnet50, resnet101, resnet152, resnet200]: - TEST_CASES.append([model, *case]) +for params in dict_product( + model=MODEL_LIST, + case=CASE_LIST, +): + TEST_CASES.append([params["model"], *params["case"]]) TEST_CASES_TS = [] -for case in [TEST_CASE_1]: - for model in [resnet10, resnet18, resnet34, resnet50, resnet101, resnet152, resnet200]: - TEST_CASES_TS.append([model, *case]) +for params in dict_product( + model=MODEL_LIST, + case=[TEST_CASE_1], +): + TEST_CASES_TS.append([params["model"], *params["case"]]) @SkipIfBeforePyTorchVersion((1, 12)) diff --git a/tests/apps/detection/test_box_transform.py b/tests/apps/detection/test_box_transform.py index 56929eafc2..efc4a305c6 100644 --- a/tests/apps/detection/test_box_transform.py +++ b/tests/apps/detection/test_box_transform.py @@ -36,20 +36,23 @@ ) from monai.data.meta_tensor import MetaTensor from monai.transforms import CastToTyped, Invertd -from tests.test_utils import TEST_NDARRAYS, assert_allclose +from tests.test_utils import TEST_NDARRAYS, assert_allclose, dict_product -TESTS_3D = [] -boxes = [[0, 0, 0, 0, 0, 0], [0, 1, 0, 2, 3, 3], [0, 1, 1, 2, 3, 4]] -labels = [1, 1, 0] -scores = [[0.2, 0.8], [0.3, 0.7], [0.6, 0.4]] -image_size = [1, 4, 6, 4] -image = np.zeros(image_size) +# Define common test data +boxes_3d = [[0, 0, 0, 0, 0, 0], [0, 1, 0, 2, 3, 3], [0, 1, 1, 2, 3, 4]] +labels_3d = [1, 1, 0] +scores_3d = [[0.2, 0.8], [0.3, 0.7], [0.6, 0.4]] +image_size_3d = [1, 4, 6, 4] +image_3d = np.zeros(image_size_3d) -for p in TEST_NDARRAYS: +# Use dict_product for TESTS_3D +TESTS_3D = [] +for params in dict_product(ndarray_type=TEST_NDARRAYS): + p = params["ndarray_type"] TESTS_3D.append( [ {"box_keys": "boxes", "dst_mode": "xyzwhd"}, - {"boxes": p(boxes), "image": p(image), "labels": p(labels), "scores": p(scores)}, + {"boxes": p(boxes_3d), "image": p(image_3d), "labels": p(labels_3d), "scores": p(scores_3d)}, p([[0, 0, 0, 0, 0, 0], [0, 1, 0, 2, 2, 3], [0, 1, 1, 2, 2, 3]]), p([[0, 0, 0, 0, 0, 0], [0, 3, 0, 1, 9, 4.5], [0, 3, 1.5, 1, 9, 6]]), p([[1, -6, -1, 1, -6, -1], [1, -3, -1, 2, 3, 3.5], [1, -3, 0.5, 2, 3, 5]]), @@ -59,23 +62,32 @@ ] ) +# 2D test data +boxes_2d = [[0, 1, 2, 2], [0, 0, 1, 1]] +labels_2d = [1, 0] +image_size_2d = [1, 2, 2] +image_2d = np.zeros(image_size_2d) + +# Use dict_product for TESTS_2D TESTS_2D = [] -boxes = [[0, 1, 2, 2], [0, 0, 1, 1]] -labels = [1, 0] -image_size = [1, 2, 2] -image = np.zeros(image_size) -for p in TEST_NDARRAYS: +for params in dict_product(ndarray_type=TEST_NDARRAYS): + p = params["ndarray_type"] TESTS_2D.append( - [{"boxes": p(boxes), "image": p(image), "labels": p(labels)}, p([[[0, 2], [0, 2]], [[1, 0], [0, 0]]])] + [{"boxes": p(boxes_2d), "image": p(image_2d), "labels": p(labels_2d)}, + p([[[0, 2], [0, 2]], [[1, 0], [0, 0]]])] ) +# Use dict_product for TESTS_2D_mask TESTS_2D_mask = [] -boxes_mask = [[[-1, 0], [0, -1]]] -for p in TEST_NDARRAYS: - TESTS_2D_mask.append([p(boxes_mask), (p([[0.0, 0.0, 2.0, 2.0]]), p([0]))]) -boxes_mask = [[[-1, 0], [0, -1]], [[-1, 1], [1, -1]]] -for p in TEST_NDARRAYS: - TESTS_2D_mask.append([p(boxes_mask), (p([[0.0, 0.0, 2.0, 2.0], [0.0, 0.0, 2.0, 2.0]]), p([0, 1]))]) +boxes_mask_1 = [[[-1, 0], [0, -1]]] +for params in dict_product(ndarray_type=TEST_NDARRAYS): + p = params["ndarray_type"] + TESTS_2D_mask.append([p(boxes_mask_1), (p([[0.0, 0.0, 2.0, 2.0]]), p([0]))]) + +boxes_mask_2 = [[[-1, 0], [0, -1]], [[-1, 1], [1, -1]]] +for params in dict_product(ndarray_type=TEST_NDARRAYS): + p = params["ndarray_type"] + TESTS_2D_mask.append([p(boxes_mask_2), (p([[0.0, 0.0, 2.0, 2.0], [0.0, 0.0, 2.0, 2.0]]), p([0, 1]))]) class TestBoxTransform(unittest.TestCase): diff --git a/tests/data/meta_tensor/test_meta_tensor.py b/tests/data/meta_tensor/test_meta_tensor.py index f52d70e7b6..079b92b9f0 100644 --- a/tests/data/meta_tensor/test_meta_tensor.py +++ b/tests/data/meta_tensor/test_meta_tensor.py @@ -32,13 +32,17 @@ from monai.data.utils import decollate_batch, list_data_collate from monai.transforms import BorderPadd, Compose, DivisiblePadd, FromMetaTensord, ToMetaTensord from monai.utils.enums import PostFix -from tests.test_utils import TEST_DEVICES, SkipIfBeforePyTorchVersion, assert_allclose, skip_if_no_cuda +from tests.test_utils import TEST_DEVICES, SkipIfBeforePyTorchVersion, assert_allclose, dict_product, skip_if_no_cuda DTYPES = [[torch.float32], [torch.float64], [torch.float16], [torch.int64], [torch.int32], [None]] + +# Replace nested loops with dict_product TESTS = [] -for _device in TEST_DEVICES: - for _dtype in DTYPES: - TESTS.append((*_device, *_dtype)) # type: ignore +for params in dict_product( + device=TEST_DEVICES, + dtype=DTYPES +): + TESTS.append((*params["device"], *params["dtype"])) # type: ignore def rand_string(min_len=5, max_len=10): diff --git a/tests/networks/blocks/test_patchembedding.py b/tests/networks/blocks/test_patchembedding.py index 95ca95b36a..6296551a79 100644 --- a/tests/networks/blocks/test_patchembedding.py +++ b/tests/networks/blocks/test_patchembedding.py @@ -21,58 +21,61 @@ from monai.networks import eval_mode from monai.networks.blocks.patchembedding import PatchEmbed, PatchEmbeddingBlock from monai.utils import optional_import -from tests.test_utils import SkipIfBeforePyTorchVersion +from tests.test_utils import SkipIfBeforePyTorchVersion, dict_product einops, has_einops = optional_import("einops") TEST_CASE_PATCHEMBEDDINGBLOCK = [] -for dropout_rate in (0.5,): - for in_channels in [1, 4]: - for hidden_size in [96, 288]: - for img_size in [32, 64]: - for patch_size in [8, 16]: - for num_heads in [8, 12]: - for proj_type in ["conv", "perceptron"]: - for pos_embed_type in ["none", "learnable", "sincos"]: - # for classification in (False, True): # TODO: add classification tests - for nd in (2, 3): - test_case = [ - { - "in_channels": in_channels, - "img_size": (img_size,) * nd, - "patch_size": (patch_size,) * nd, - "hidden_size": hidden_size, - "num_heads": num_heads, - "proj_type": proj_type, - "pos_embed_type": pos_embed_type, - "dropout_rate": dropout_rate, - }, - (2, in_channels, *([img_size] * nd)), - (2, (img_size // patch_size) ** nd, hidden_size), - ] - if nd == 2: - test_case[0]["spatial_dims"] = 2 # type: ignore - TEST_CASE_PATCHEMBEDDINGBLOCK.append(test_case) +for params in dict_product( + dropout_rate=[0.5], + in_channels=[1, 4], + hidden_size=[96, 288], + img_size=[32, 64], + patch_size=[8, 16], + num_heads=[8, 12], + proj_type=["conv", "perceptron"], + pos_embed_type=["none", "learnable", "sincos"], + nd=[2, 3], +): + test_case = [ + { + "in_channels": params["in_channels"], + "img_size": (params["img_size"],) * params["nd"], + "patch_size": (params["patch_size"],) * params["nd"], + "hidden_size": params["hidden_size"], + "num_heads": params["num_heads"], + "proj_type": params["proj_type"], + "pos_embed_type": params["pos_embed_type"], + "dropout_rate": params["dropout_rate"], + }, + (2, params["in_channels"], *[params["img_size"]] * params["nd"]), + (2, (params["img_size"] // params["patch_size"]) ** params["nd"], params["hidden_size"]), + ] + if params["nd"] == 2: + test_case[0]["spatial_dims"] = 2 + TEST_CASE_PATCHEMBEDDINGBLOCK.append(test_case) TEST_CASE_PATCHEMBED = [] -for patch_size in [2]: - for in_chans in [1, 4]: - for img_size in [96]: - for embed_dim in [6, 12]: - for norm_layer in [nn.LayerNorm]: - for nd in [2, 3]: - test_case = [ - { - "patch_size": (patch_size,) * nd, - "in_chans": in_chans, - "embed_dim": embed_dim, - "norm_layer": norm_layer, - "spatial_dims": nd, - }, - (2, in_chans, *([img_size] * nd)), - (2, embed_dim, *([img_size // patch_size] * nd)), - ] - TEST_CASE_PATCHEMBED.append(test_case) +for params in dict_product( + patch_size=[2], + in_chans=[1, 4], + img_size=[96], + embed_dim=[6, 12], + norm_layer=[nn.LayerNorm], + nd=[2, 3], +): + test_case = [ + { + "patch_size": (params["patch_size"],) * params["nd"], + "in_chans": params["in_chans"], + "embed_dim": params["embed_dim"], + "norm_layer": params["norm_layer"], + "spatial_dims": params["nd"], + }, + (2, params["in_chans"], *[params["img_size"]] * params["nd"]), + (2, params["embed_dim"], *[params["img_size"] // params["patch_size"]] * params["nd"]), + ] + TEST_CASE_PATCHEMBED.append(test_case) @SkipIfBeforePyTorchVersion((1, 11, 1)) diff --git a/tests/networks/blocks/test_selfattention.py b/tests/networks/blocks/test_selfattention.py index 494f64cad8..3a105e63a7 100644 --- a/tests/networks/blocks/test_selfattention.py +++ b/tests/networks/blocks/test_selfattention.py @@ -22,33 +22,35 @@ from monai.networks.blocks.selfattention import SABlock from monai.networks.layers.factories import RelPosEmbedding from monai.utils import optional_import -from tests.test_utils import SkipIfBeforePyTorchVersion, assert_allclose, test_script_save +from tests.test_utils import SkipIfBeforePyTorchVersion, assert_allclose, dict_product, test_script_save einops, has_einops = optional_import("einops") TEST_CASE_SABLOCK = [] -for dropout_rate in np.linspace(0, 1, 4): - for hidden_size in [360, 480, 600, 768]: - for num_heads in [4, 6, 8, 12]: - for rel_pos_embedding in [None, RelPosEmbedding.DECOMPOSED]: - for input_size in [(16, 32), (8, 8, 8)]: - for include_fc in [True, False]: - for use_combined_linear in [True, False]: - test_case = [ - { - "hidden_size": hidden_size, - "num_heads": num_heads, - "dropout_rate": dropout_rate, - "rel_pos_embedding": rel_pos_embedding, - "input_size": input_size, - "include_fc": include_fc, - "use_combined_linear": use_combined_linear, - "use_flash_attention": True if rel_pos_embedding is None else False, - }, - (2, 512, hidden_size), - (2, 512, hidden_size), - ] - TEST_CASE_SABLOCK.append(test_case) +for params in dict_product( + dropout_rate=np.linspace(0, 1, 4), + hidden_size=[360, 480, 600, 768], + num_heads=[4, 6, 8, 12], + rel_pos_embedding=[None, RelPosEmbedding.DECOMPOSED], + input_size=[(16, 32), (8, 8, 8)], + include_fc=[True, False], + use_combined_linear=[True, False], +): + test_case = [ + { + "hidden_size": params["hidden_size"], + "num_heads": params["num_heads"], + "dropout_rate": params["dropout_rate"], + "rel_pos_embedding": params["rel_pos_embedding"], + "input_size": params["input_size"], + "include_fc": params["include_fc"], + "use_combined_linear": params["use_combined_linear"], + "use_flash_attention": True if params["rel_pos_embedding"] is None else False, + }, + (2, 512, params["hidden_size"]), + (2, 512, params["hidden_size"]), + ] + TEST_CASE_SABLOCK.append(test_case) class TestResBlock(unittest.TestCase):