class_docstr: A Python-based replay buffer that supports uniform sampling.
  
  Writing and reading to this replay buffer is thread safe.
  
  This replay buffer can be subclassed to change the encoding used for the
  underlying storage by overriding _encoded_data_spec, _encode, _decode, and
  _on_delete.
class_docstr_tok: ["A","Python-based","replay","buffer","that","supports","uniform","sampling",".","Writing","and","reading","to","this","replay","buffer","is","thread","safe",".","This","replay","buffer","can","be","subclassed","to","change","the","encoding","used","for","the","underlying","storage","by","overriding","_encoded_data_spec",",","_encode",",","_decode",",","and","_on_delete","."]
code: def _as_dataset(
      self,
      sample_batch_size=None,
      num_steps=None,
      sequence_preprocess_fn=None,
      num_parallel_calls=None,
  ):
      if sequence_preprocess_fn is not None:
          raise NotImplementedError(
              "sequence_preprocess_fn is not supported."
          )
      if num_parallel_calls is not None:
          raise NotImplementedError(
              "PyUniformReplayBuffer does not support "
              "num_parallel_calls (must be None)."
          )
  
      data_spec = self._data_spec
      if sample_batch_size is not None:
          data_spec = array_spec.add_outer_dims_nest(
              data_spec, (sample_batch_size,)
          )
      if num_steps is not None:
          data_spec = (data_spec,) * num_steps
      shapes = tuple(s.shape for s in tf.nest.flatten(data_spec))
      dtypes = tuple(s.dtype for s in tf.nest.flatten(data_spec))
  
      def generator_fn():
          while True:
              if sample_batch_size is not None:
                  batch = [
                      self._get_next(
                          num_steps=num_steps, time_stacked=False
                      )
                      for _ in range(sample_batch_size)
                  ]
                  item = nest_utils.stack_nested_arrays(batch)
              else:
                  item = self._get_next(
                      num_steps=num_steps, time_stacked=False
                  )
              yield tuple(tf.nest.flatten(item))
  
      def time_stack(*structures):
          time_axis = 0 if sample_batch_size is None else 1
          return tf.nest.map_structure(
              lambda *elements: tf.stack(elements, axis=time_axis),
              *structures,
          )
  
      ds = tf.data.Dataset.from_generator(
          generator_fn, dtypes, shapes
      ).map(lambda *items: tf.nest.pack_sequence_as(data_spec, items))
      if num_steps is not None:
          return ds.map(time_stack)
      else:
          return ds
  
imports: from __future__ import absolute_import
  from __future__ import division
  from __future__ import print_function
  import threading
  import numpy
  import tensorflow
  from tf_agents.replay_buffers import replay_buffer
  from tf_agents.specs import array_spec
  from tf_agents.utils import nest_utils
  from tf_agents.utils import numpy_storage
label_desc: Use image node_id 10 for calling the PyUniformReplayBuffer obj's underlying member method code with example usage: obj._as_dataset(sample_batch_size, num_steps, sequence_preprocess_fn, num_parallel_calls) and returns: tf, ds, ds