class_docstr: Class that implements an adapted UNet. This class also serve as the parent class of LocalNet and GlobalNet
  
  Reference:
      O. Ronneberger, P. Fischer, and T. Brox,
      “U-net: Convolutional networks for biomedical image segmentation,”,
      Lecture Notes in Computer Science, 2015, vol. 9351, pp. 234–241.
      https://arxiv.org/abs/1505.04597
  
  Adapted from:
      DeepReg (https://github.com/DeepRegNet/DeepReg)
docstr: Args:
      spatial_dims: number of spatial dims
      in_channels: number of input channels
      num_channel_initial: number of initial channels
      depth: input is at level 0, bottom is at level depth.
      out_kernel_initializer: kernel initializer for the last layer
      out_activation: activation at the last layer
      out_channels: number of channels for the output
      extract_levels: list, which levels from net to extract. The maximum level must equal to ``depth``
      pooling: for down-sampling, use non-parameterized pooling if true, otherwise use conv
      concat_skip: when up-sampling, concatenate skipped tensor if true, otherwise use addition
      encode_kernel_sizes: kernel size for down-sampling
docstr_tok: ["Args",":","spatial_dims",":","number","of","spatial","dims","in_channels",":","number","of","input","channels","num_channel_initial",":","number","of","initial","channels","depth",":","input","is","at","level","0",",","bottom","is","at","level","depth",".","out_kernel_initializer",":","kernel","initializer","for","the","last","layer","out_activation",":","activation","at","the","last","layer","out_channels",":","number","of","channels","for","the","output","extract_levels",":","list",",","which","levels","from","net","to","extract",".","The","maximum","level","must","equal","to","``","depth","``","pooling",":","for","down-sampling",",","use","non-parameterized","pooling","if","true",",","otherwise","use","conv","concat_skip",":","when","up-sampling",",","concatenate","skipped","tensor","if","true",",","otherwise","use","addition","encode_kernel_sizes",":","kernel","size","for","down-sampling"]
code: def __init__(
      self,
      spatial_dims: int,
      in_channels: int,
      num_channel_initial: int,
      depth: int,
      out_kernel_initializer: str | None = "kaiming_uniform",
      out_activation: str | None = None,
      out_channels: int = 3,
      extract_levels: tuple[int] | None = None,
      pooling: bool = True,
      concat_skip: bool = False,
      encode_kernel_sizes: int | list[int] = 3,
  ):
      """
      Args:
          spatial_dims: number of spatial dims
          in_channels: number of input channels
          num_channel_initial: number of initial channels
          depth: input is at level 0, bottom is at level depth.
          out_kernel_initializer: kernel initializer for the last layer
          out_activation: activation at the last layer
          out_channels: number of channels for the output
          extract_levels: list, which levels from net to extract. The maximum level must equal to ``depth``
          pooling: for down-sampling, use non-parameterized pooling if true, otherwise use conv
          concat_skip: when up-sampling, concatenate skipped tensor if true, otherwise use addition
          encode_kernel_sizes: kernel size for down-sampling
      """
      super().__init__()
      if not extract_levels:
          extract_levels = (depth,)
      if max(extract_levels) != depth:
          raise AssertionError
  
      # save parameters
      self.spatial_dims = spatial_dims
      self.in_channels = in_channels
      self.num_channel_initial = num_channel_initial
      self.depth = depth
      self.out_kernel_initializer = out_kernel_initializer
      self.out_activation = out_activation
      self.out_channels = out_channels
      self.extract_levels = extract_levels
      self.pooling = pooling
      self.concat_skip = concat_skip
  
      if isinstance(encode_kernel_sizes, int):
          encode_kernel_sizes = [encode_kernel_sizes] * (self.depth + 1)
      if len(encode_kernel_sizes) != self.depth + 1:
          raise AssertionError
      self.encode_kernel_sizes: list[int] = encode_kernel_sizes
  
      self.num_channels = [
          self.num_channel_initial * (2**d)
          for d in range(self.depth + 1)
      ]
      self.min_extract_level = min(self.extract_levels)
  
      # init layers
      # all lists start with d = 0
      self.encode_convs: nn.ModuleList
      self.encode_pools: nn.ModuleList
      self.bottom_block: nn.Sequential
      self.decode_deconvs: nn.ModuleList
      self.decode_convs: nn.ModuleList
      self.output_block: nn.Module
  
      # build layers
      self.build_layers()
  
imports: from __future__ import annotations
  import torch
  from torch import nn
  from torch.nn import functional
  from monai.networks.blocks.regunet_block import RegistrationDownSampleBlock, RegistrationExtractionBlock, RegistrationResidualConvBlock, get_conv_block, get_deconv_block
  from monai.networks.utils import meshgrid_ij
label_desc: Use image node_id 1 to create a new RegUNet object from inherited base classes: nn with example: obj = RegUNet(spatial_dims, in_channels, num_channel_initial, depth, out_kernel_initializer, out_activation, out_channels, extract_levels, pooling, concat_skip, encode_kernel_sizes)