code: def register_scalers(
      target_spaces: _PRUNING_TARGET_SPACES
      | _QUANTIZATION_TARGET_SPACES,
      set_default_granularity: Callable[[TargetSpace], Any],
  ):
      """
      Create and register scaler to the target space according to the granularity of target space.
      Four string type granularity will be treated specially:
  
          * ``default`` will be treated by function ``set_default_granularity``.
          * ``in_channel`` means compressing on the 0-th dim of the paramter target.
          * ``out_channel`` means compressing on the 1-th dim of the paramter target.
          * ``per_channel`` means compressing on the 1-th dim of the input/output target (assume 0-th dim is batch dim).
  
      Parameters
      ----------
      target_spaces
          {module_name: {target_name: target_space}}.
      set_default_granularity
          A callable function, given a target space and return a scaler.
      """
      # scalers are used to support different sparse/quant granularity
      for _, ts in target_spaces.items():
          for _, target_space in ts.items():
              if target_space.granularity == "default":
                  target_space.granularity = set_default_granularity(
                      target_space
                  )
              if target_space.granularity is None:
                  continue
              if target_space.granularity == "out_channel":
                  assert (
                      target_space._target_type is TargetType.PARAMETER
                  )
                  target_space._scaler = Scaling(
                      [1],
                      kernel_padding_mode="back",
                      kernel_padding_val=-1,
                  )
              elif target_space.granularity == "in_channel":
                  assert (
                      target_space._target_type is TargetType.PARAMETER
                  )
                  target_space._scaler = Scaling(
                      [-1, 1],
                      kernel_padding_mode="back",
                      kernel_padding_val=-1,
                  )
              elif target_space.granularity == "per_channel":
                  # NOTE: here assume dim 0 is batch, dim 1 is channel
                  assert target_space._target_type in [
                      TargetType.INPUT,
                      TargetType.OUTPUT,
                  ]
                  target_space._scaler = Scaling(
                      [-1, 1],
                      kernel_padding_mode="back",
                      kernel_padding_val=-1,
                  )
              else:
                  kernel_padding_mode = None
                  kernel_padding_val = None
                  if all(
                      isinstance(_, int)
                      for _ in target_space.granularity
                  ):
                      kernel_size = target_space.granularity
                  elif len(target_space.granularity) == 1:
                      kernel_size = target_space.granularity[0]
                  elif len(target_space.granularity) == 2:
                      kernel_size, kernel_padding_mode = (
                          target_space.granularity[0],
                          target_space.granularity[1],
                      )
                  else:
                      assert len(target_space.granularity) == 3
                      kernel_size = target_space.granularity[0]
                      kernel_padding_mode = target_space.granularity[1]
                      kernel_padding_val = target_space.granularity[2]
                  kernel_padding_mode = (
                      kernel_padding_mode
                      if kernel_padding_mode
                      else "front"
                  )
                  kernel_padding_val = (
                      kernel_padding_val if kernel_padding_val else 1
                  )
                  target_space._scaler = Scaling(
                      kernel_size,
                      kernel_padding_mode,
                      kernel_padding_val,
                  )
  
imports: from __future__ import annotations
  from collections import defaultdict
  from copy import deepcopy
  import logging
  from typing import Any, Dict, List, Literal, Callable
  import torch
  from torch.utils._pytree import tree_map
  from .config import trans_legacy_config_list, default_config_schema
  from .target_space import TargetSpace, TargetType, DistillationTargetSpace, PruningTargetSpace, QuantizationTargetSpace
  from .wrapper import ModuleWrapper, register_wrappers
  from ..utils import Evaluator, Scaling, _EVALUATOR_DOCSTRING
label_desc: Use image node_id 1 for calling a global function with example usage: register_scalers(target_spaces, set_default_granularity) without return types