code: def _approx_eq_iterables(val: Any, other: Any, *,
                           atol: Union[int, float]) -> bool:
      
  
      def get_iter(iterable):
          try:
              return iter(iterable)
          except TypeError:
              return None
  
      val_it = get_iter(val)
      other_it = get_iter(other)
  
      if val_it is not None and other_it is not None:
          while True:
              try:
                  val_next = next(val_it)
              except StopIteration:
                  try:
                      next(other_it)
                      return False
                  except StopIteration:
                      return True
  
              try:
                  other_next = next(other_it)
              except StopIteration:
                  return False
  
              result = approx_eq(val_next, other_next, atol=atol)
              if result is not True:
                  return result
  
      return NotImplemented
docs: Iterates over arguments and calls approx_eq recursively.
  
      Types of `val` and `other` does not necessarily needs to match each other.
      They just need to be iterable of the same length and have the same
      structure, approx_eq() will be called on each consecutive element of `val`
      and `other`.
  
      Args:
          val: Source for approximate comparison.
          other: Target for approximate comparison.
          atol: The minimum absolute tolerance. See np.isclose() documentation for
                details.
  
      Returns:
          True if objects are approximately equal, False otherwise. Returns
          NotImplemented when approximate equality is not implemented for given
          types.