class_docstr: Reimplementation of DiNTS based on
  "DiNTS: Differentiable Neural Network Topology Search for 3D Medical Image Segmentation
  <https://arxiv.org/abs/2103.15954>".
  
  The model contains a pre-defined multi-resolution stem block (defined in this class) and a
  DiNTS space (defined in :py:class:`monai.networks.nets.TopologyInstance` and
  :py:class:`monai.networks.nets.TopologySearch`).
  
  The stem block is for: 1) input downsample and 2) output upsample to original size.
  The model downsamples the input image by 2 (if ``use_downsample=True``).
  The downsampled image is downsampled by [1, 2, 4, 8] times (``num_depths=4``) and used as input to the
  DiNTS search space (``TopologySearch``) or the DiNTS instance (``TopologyInstance``).
  
      - ``TopologyInstance`` is the final searched model. The initialization requires the searched architecture codes.
      - ``TopologySearch`` is a multi-path topology and cell operation search space.
        The architecture codes will be initialized as one.
      - ``TopologyConstruction`` is the parent class which constructs the instance and search space.
  
  To meet the requirements of the structure, the input size for each spatial dimension should be:
  divisible by 2 ** (num_depths + 1).
  
  Args:
      dints_space: DiNTS search space. The value should be instance of `TopologyInstance` or `TopologySearch`.
      in_channels: number of input image channels.
      num_classes: number of output segmentation classes.
      act_name: activation name, default to 'RELU'.
      norm_name: normalization used in convolution blocks. Default to `InstanceNorm`.
      spatial_dims: spatial 2D or 3D inputs.
      use_downsample: use downsample in the stem.
          If ``False``, the search space will be in resolution [1, 1/2, 1/4, 1/8],
          if ``True``, the search space will be in resolution [1/2, 1/4, 1/8, 1/16].
      node_a: node activation numpy matrix. Its shape is `(num_depths, num_blocks + 1)`.
          +1 for multi-resolution inputs.
          In model searching stage, ``node_a`` can be None. In deployment stage, ``node_a`` cannot be None.
class_docstr_tok: ["Reimplementation","of","DiNTS","based","on","''","DiNTS",":","Differentiable","Neural","Network","Topology","Search","for","3D","Medical","Image","Segmentation","<","https",":","\/\/arxiv.org\/abs\/2103.15954",">","''",".","The","model","contains","a","pre-defined","multi-resolution","stem","block","(","defined","in","this","class",")","and","a","DiNTS","space","(","defined","in",":","py",":","class",":","`","monai.networks.nets.TopologyInstance","`","and",":","py",":","class",":","`","monai.networks.nets.TopologySearch","`",")",".","The","stem","block","is","for",":","1",")","input","downsample","and","2",")","output","upsample","to","original","size",".","The","model","downsamples","the","input","image","by","2","(","if","``","use_downsample=True","``",")",".","The","downsampled","image","is","downsampled","by","[","1",",","2",",","4",",","8","]","times","(","``","num_depths=4","``",")","and","used","as","input","to","the","DiNTS","search","space","(","``","TopologySearch","``",")","or","the","DiNTS","instance","(","``","TopologyInstance","``",")",".","-","``","TopologyInstance","``","is","the","final","searched","model",".","The","initialization","requires","the","searched","architecture","codes",".","-","``","TopologySearch","``","is","a","multi-path","topology","and","cell","operation","search","space",".","The","architecture","codes","will","be","initialized","as","one",".","-","``","TopologyConstruction","``","is","the","parent","class","which","constructs","the","instance","and","search","space",".","To","meet","the","requirements","of","the","structure",",","the","input","size","for","each","spatial","dimension","should","be",":","divisible","by","2","*","*","(","num_depths","+","1",")",".","Args",":","dints_space",":","DiNTS","search","space",".","The","value","should","be","instance","of","`","TopologyInstance","`","or","`","TopologySearch","`",".","in_channels",":","number","of","input","image","channels",".","num_classes",":","number","of","output","segmentation","classes",".","act_name",":","activation","name",",","default","to","'RELU","'",".","norm_name",":","normalization","used","in","convolution","blocks",".","Default","to","`","InstanceNorm","`",".","spatial_dims",":","spatial","2D","or","3D","inputs",".","use_downsample",":","use","downsample","in","the","stem",".","If","``","False","``",",","the","search","space","will","be","in","resolution","[","1",",","1\/2",",","1\/4",",","1\/8","]",",","if","``","True","``",",","the","search","space","will","be","in","resolution","[","1\/2",",","1\/4",",","1\/8",",","1\/16","]",".","node_a",":","node","activation","numpy","matrix",".","Its","shape","is","`","(","num_depths",",","num_blocks","+","1",")","`",".","+1","for","multi-resolution","inputs",".","In","model","searching","stage",",","``","node_a","``","can","be","None",".","In","deployment","stage",",","``","node_a","``","can","not","be","None","."]
code: def __init__(
      self,
      dints_space,
      in_channels: int,
      num_classes: int,
      act_name: tuple | str = "RELU",
      norm_name: tuple | str = ("INSTANCE", {"affine": True}),
      spatial_dims: int = 3,
      use_downsample: bool = True,
      node_a=None,
  ):
      super().__init__()
  
      self.dints_space = dints_space
      self.filter_nums = dints_space.filter_nums
      self.num_blocks = dints_space.num_blocks
      self.num_depths = dints_space.num_depths
      if spatial_dims not in (2, 3):
          raise NotImplementedError(
              f"Spatial dimensions {spatial_dims} is not supported."
          )
      self._spatial_dims = spatial_dims
      if node_a is None:
          self.node_a = torch.ones(
              (self.num_blocks + 1, self.num_depths)
          )
      else:
          self.node_a = node_a
  
      # define stem operations for every block
      conv_type = Conv[Conv.CONV, spatial_dims]
      self.stem_down = nn.ModuleDict()
      self.stem_up = nn.ModuleDict()
      self.stem_finals = nn.Sequential(
          ActiConvNormBlock(
              self.filter_nums[0],
              self.filter_nums[0],
              act_name=act_name,
              norm_name=norm_name,
              spatial_dims=spatial_dims,
          ),
          conv_type(
              in_channels=self.filter_nums[0],
              out_channels=num_classes,
              kernel_size=1,
              stride=1,
              padding=0,
              groups=1,
              bias=True,
              dilation=1,
          ),
      )
      mode = "trilinear" if self._spatial_dims == 3 else "bilinear"
      for res_idx in range(self.num_depths):
          # define downsample stems before DiNTS search
          if use_downsample:
              self.stem_down[str(res_idx)] = StemTS(
                  nn.Upsample(
                      scale_factor=1 / (2**res_idx),
                      mode=mode,
                      align_corners=True,
                  ),
                  conv_type(
                      in_channels=in_channels,
                      out_channels=self.filter_nums[res_idx],
                      kernel_size=3,
                      stride=1,
                      padding=1,
                      groups=1,
                      bias=False,
                      dilation=1,
                  ),
                  get_norm_layer(
                      name=norm_name,
                      spatial_dims=spatial_dims,
                      channels=self.filter_nums[res_idx],
                  ),
                  get_act_layer(name=act_name),
                  conv_type(
                      in_channels=self.filter_nums[res_idx],
                      out_channels=self.filter_nums[res_idx + 1],
                      kernel_size=3,
                      stride=2,
                      padding=1,
                      groups=1,
                      bias=False,
                      dilation=1,
                  ),
                  get_norm_layer(
                      name=norm_name,
                      spatial_dims=spatial_dims,
                      channels=self.filter_nums[res_idx + 1],
                  ),
              )
              self.stem_up[str(res_idx)] = StemTS(
                  get_act_layer(name=act_name),
                  conv_type(
                      in_channels=self.filter_nums[res_idx + 1],
                      out_channels=self.filter_nums[res_idx],
                      kernel_size=3,
                      stride=1,
                      padding=1,
                      groups=1,
                      bias=False,
                      dilation=1,
                  ),
                  get_norm_layer(
                      name=norm_name,
                      spatial_dims=spatial_dims,
                      channels=self.filter_nums[res_idx],
                  ),
                  nn.Upsample(
                      scale_factor=2, mode=mode, align_corners=True
                  ),
              )
  
          else:
              self.stem_down[str(res_idx)] = StemTS(
                  nn.Upsample(
                      scale_factor=1 / (2**res_idx),
                      mode=mode,
                      align_corners=True,
                  ),
                  conv_type(
                      in_channels=in_channels,
                      out_channels=self.filter_nums[res_idx],
                      kernel_size=3,
                      stride=1,
                      padding=1,
                      groups=1,
                      bias=False,
                      dilation=1,
                  ),
                  get_norm_layer(
                      name=norm_name,
                      spatial_dims=spatial_dims,
                      channels=self.filter_nums[res_idx],
                  ),
              )
              self.stem_up[str(res_idx)] = StemTS(
                  get_act_layer(name=act_name),
                  conv_type(
                      in_channels=self.filter_nums[res_idx],
                      out_channels=self.filter_nums[
                          max(res_idx - 1, 0)
                      ],
                      kernel_size=3,
                      stride=1,
                      padding=1,
                      groups=1,
                      bias=False,
                      dilation=1,
                  ),
                  get_norm_layer(
                      name=norm_name,
                      spatial_dims=spatial_dims,
                      channels=self.filter_nums[max(res_idx - 1, 0)],
                  ),
                  nn.Upsample(
                      scale_factor=2 ** (res_idx != 0),
                      mode=mode,
                      align_corners=True,
                  ),
              )
  
imports: from __future__ import annotations
  import datetime
  import warnings
  from typing import Optional
  import numpy
  import torch
  import torch.nn
  import torch.nn.functional
  from monai.networks.blocks.dints_block import ActiConvNormBlock, FactorizedIncreaseBlock, FactorizedReduceBlock, P3DActiConvNormBlock
  from monai.networks.layers.factories import Conv
  from monai.networks.layers.utils import get_act_layer, get_norm_layer
  from monai.utils import optional_import
label_desc: Use image node_id 1 to create a new DiNTS object from inherited base classes: nn with example: obj = DiNTS(dints_space, in_channels, num_classes, act_name, norm_name, spatial_dims, use_downsample, node_a)