class_docstr: A Wrapper for tf.train.Optimizer.
  
  Automatically takes care of:
  - Gradient averaging for multi-GPU training.
  - Gradient accumulation for arbitrarily large minibatches.
  - Dynamic loss scaling and typecasts for FP16 training.
  - Ignoring corrupted gradients that contain NaNs/Infs.
  - Reporting statistics.
  - Well-chosen default settings.
class_docstr_tok: ["A","Wrapper","for","tf.train.Optimizer",".","Automatically","takes","care","of",":","-","Gradient","averaging","for","multi-GPU","training",".","-","Gradient","accumulation","for","arbitrarily","large","minibatches",".","-","Dynamic","loss","scaling","and","typecasts","for","FP16","training",".","-","Ignoring","corrupted","gradients","that","contain","NaNs\/Infs",".","-","Reporting","statistics",".","-","Well-chosen","default","settings","."]
code: def __init__(
      self,
      name: str = "Train",  # Name string that will appear in TensorFlow graph.
      tf_optimizer: str = "tf.train.AdamOptimizer",  # Underlying optimizer class.
      learning_rate: TfExpressionEx = 0.001,  # Learning rate. Can vary over time.
      minibatch_multiplier: TfExpressionEx = None,  # Treat N consecutive minibatches as one by accumulating gradients.
      share: "Optimizer" = None,  # Share internal state with a previously created optimizer?
      use_loss_scaling: bool = False,  # Enable dynamic loss scaling for robust mixed-precision training?
      loss_scaling_init: float = 64.0,  # Log2 of initial loss scaling factor.
      loss_scaling_inc: float = 0.0005,  # Log2 of per-minibatch loss scaling increment when there is no overflow.
      loss_scaling_dec: float = 1.0,  # Log2 of per-minibatch loss scaling decrement when there is an overflow.
      report_mem_usage: bool = False,  # Report fine-grained memory usage statistics in TensorBoard?
      **kwargs,
  ):
      # Public fields.
      self.name = name
      self.learning_rate = learning_rate
      self.minibatch_multiplier = minibatch_multiplier
      self.id = self.name.replace("/", ".")
      self.scope = tf.get_default_graph().unique_name(self.id)
      self.optimizer_class = util.get_obj_by_name(tf_optimizer)
      self.optimizer_kwargs = dict(kwargs)
      self.use_loss_scaling = use_loss_scaling
      self.loss_scaling_init = loss_scaling_init
      self.loss_scaling_inc = loss_scaling_inc
      self.loss_scaling_dec = loss_scaling_dec
  
      # Private fields.
      self._updates_applied = False
      self._devices = OrderedDict()  # device_name => EasyDict()
      self._shared_optimizers = (
          OrderedDict()
      )  # device_name => optimizer_class
      self._gradient_shapes = None  # [shape, ...]
      self._report_mem_usage = report_mem_usage
  
      # Validate arguments.
      assert callable(self.optimizer_class)
  
      # Share internal state if requested.
      if share is not None:
          assert isinstance(share, Optimizer)
          assert self.optimizer_class is share.optimizer_class
          assert self.learning_rate is share.learning_rate
          assert self.optimizer_kwargs == share.optimizer_kwargs
          self._shared_optimizers = share._shared_optimizers
  
imports: import numpy
  import tensorflow
  from collections import OrderedDict
  from typing import List, Union
  from .None import autosummary
  from .None import tfutil
  from ..None import util
  from .tfutil import TfExpression, TfExpressionEx
label_desc: Use image node_id 1 to create a new Optimizer object  with example: obj = Optimizer(name, tf_optimizer, learning_rate, minibatch_multiplier, share, use_loss_scaling, loss_scaling_init, loss_scaling_inc, loss_scaling_dec, report_mem_usage)