class_docstr: :class:`~opacus.optimizers.optimizer.DPOptimizer` that implements
  per layer clipping strategy and is compatible with distributed data parallel
class_docstr_tok: [":","class",":","`","~opacus.optimizers.optimizer.DPOptimizer","`","that","implements","per","layer","clipping","strategy","and","is","compatible","with","distributed","data","parallel"]
code: def __init__(
      self,
      optimizer: Optimizer,
      *,
      noise_multiplier: float,
      max_grad_norm: List[float],
      expected_batch_size: Optional[int],
      loss_reduction: str = "mean",
      generator=None,
      secure_mode: bool = False,
  ):
      self.rank = torch.distributed.get_rank()
      self.world_size = torch.distributed.get_world_size()
      self.max_grad_norms = max_grad_norm
      max_grad_norm = torch.norm(
          torch.Tensor(self.max_grad_norms), p=2
      ).item()
      super().__init__(
          optimizer,
          noise_multiplier=noise_multiplier,
          max_grad_norm=max_grad_norm,
          expected_batch_size=expected_batch_size,
          loss_reduction=loss_reduction,
          generator=generator,
          secure_mode=secure_mode,
      )
      self._register_hooks()
  
imports: from __future__ import annotations
  from functools import partial
  from typing import Callable, List, Optional
  import torch
  from opt_einsum import contract
  from torch import nn
  from torch.optim import Optimizer
  from .ddpoptimizer import DistributedDPOptimizer
  from .optimizer import DPOptimizer, _generate_noise
  from .perlayeroptimizer import DPPerLayerOptimizer
label_desc: Use image node_id 1 to create a new DistributedPerLayerOptimizer object from inherited base classes: DPOptimizer with example: obj = DistributedPerLayerOptimizer(optimizer)