class_docstr: Manages all the learning details needed when training an agent.
  
  These include:
    * Using distribution strategies correctly
    * Summaries
    * Checkpoints
    * Minimizing entering/exiting TF context:
        Especially in the case of TPUs scheduling a single TPU program to
        perform multiple train steps is critical for performance.
    * Generalizes the train call to be done correctly across CPU, GPU, or TPU
      executions managed by DistributionStrategies. This uses `strategy.run` and
      then makes sure to do a reduce operation over the `LossInfo` returned by
      the agent.
class_docstr_tok: ["Manages","all","the","learning","details","needed","when","training","an","agent",".","These","include",":","*","Using","distribution","strategies","correctly","*","Summaries","*","Checkpoints","*","Minimizing","entering\/exiting","TF","context",":","Especially","in","the","case","of","TPUs","scheduling","a","single","TPU","program","to","perform","multiple","train","steps","is","critical","for","performance",".","*","Generalizes","the","train","call","to","be","done","correctly","across","CPU",",","GPU",",","or","TPU","executions","managed","by","DistributionStrategies",".","This","uses","`","strategy.run","`","and","then","makes","sure","to","do","a","reduce","operation","over","the","`","LossInfo","`","returned","by","the","agent","."]
docstr: Computes loss for the experience.
  
  Since this calls agent.loss() it does not update gradients or
  increment the train step counter. Networks are called with `training=False`
  so statistics like batch norm are not updated.
  
  Args:
    experience_and_sample_info: A batch of experience and sample info. If not
      specified, `next(self._experience_iterator)` is used.
    reduce_op: a `tf.distribute.ReduceOp` value specifying how loss values
      should be aggregated across replicas.
  
  Returns:
    The total loss computed.
docstr_tok: ["Computes","loss","for","the","experience",".","Since","this","calls","agent.loss","(",")","it","does","not","update","gradients","or","increment","the","train","step","counter",".","Networks","are","called","with","`","training=False","`","so","statistics","like","batch","norm","are","not","updated",".","Args",":","experience_and_sample_info",":","A","batch","of","experience","and","sample","info",".","If","not","specified",",","`","next","(","self._experience_iterator",")","`","is","used",".","reduce_op",":","a","`","tf.distribute.ReduceOp","`","value","specifying","how","loss","values","should","be","aggregated","across","replicas",".","Returns",":","The","total","loss","computed","."]
code: def loss(
      self,
      experience_and_sample_info: Optional[
          ExperienceAndSampleInfo
      ] = None,
      reduce_op: tf.distribute.ReduceOp = tf.distribute.ReduceOp.SUM,
  ) -> tf_agent.LossInfo:
      """Computes loss for the experience.
  
      Since this calls agent.loss() it does not update gradients or
      increment the train step counter. Networks are called with `training=False`
      so statistics like batch norm are not updated.
  
      Args:
        experience_and_sample_info: A batch of experience and sample info. If not
          specified, `next(self._experience_iterator)` is used.
        reduce_op: a `tf.distribute.ReduceOp` value specifying how loss values
          should be aggregated across replicas.
  
      Returns:
        The total loss computed.
      """
  
      def _summary_record_if():
          return tf.math.equal(
              self.train_step % tf.constant(self.summary_interval), 0
          )
  
      with self.train_summary_writer.as_default(), common.soft_device_placement(), tf.compat.v2.summary.record_if(
          _summary_record_if
      ), self.strategy.scope():
          if experience_and_sample_info is None:
              sample = next(self._experience_iterator)
              if self._direct_sampling:
                  experience_and_sample_info = (sample, None)
              elif self._use_reverb_v2:
                  experience_and_sample_info = (
                      sample.data,
                      sample.info,
                  )
              else:
                  experience_and_sample_info = sample
  
          loss_info = self._loss(experience_and_sample_info, reduce_op)
  
          return loss_info
  
file_path: agents/tf_agents/train/learner.py
imports: import os
  from typing import Any, Optional, Tuple
  from absl import logging
  import gin
  import tensorflow.compat.v2
  from tf_agents.agents import tf_agent
  from tf_agents.specs import tensor_spec
  from tf_agents.train import interval_trigger
  from tf_agents.typing import types
  from tf_agents.utils import common
label_desc: Use image node_id 7 for calling the Learner obj's underlying member method code with example usage: obj.loss(experience_and_sample_info, reduce_op) and returns: tf, loss_info