diff --git a/CHANGELOG.md b/CHANGELOG.md index fb78698..52a91b3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -19,6 +19,7 @@ instead of just `nn.Module`. #1032 - Added interfaces for most `Actor` and `Critic` classes to enforce the presence of `forward` methods. #1032 - Simplified `PGPolicy` forward by unifying the `dist_fn` interface (see associated breaking change). #1032 - Use `.mode` of distribution instead of relying on knowledge of the distribution type. #1032 +- Exception no longer raised on `len` of empty `Batch`. #1084 ### Breaking Changes diff --git a/tianshou/data/batch.py b/tianshou/data/batch.py index b9b7024..ffa7488 100644 --- a/tianshou/data/batch.py +++ b/tianshou/data/batch.py @@ -870,16 +870,17 @@ class Batch(BatchProtocol): """Return len(self).""" lens = [] for obj in self.__dict__.values(): + # TODO: causes inconsistent behavior to batch with empty batches + # and batch with empty sequences of other type. Remove, but only after + # Buffer and Collectors have been improved to no longer rely on this if isinstance(obj, Batch) and obj.is_empty(recurse=True): continue if hasattr(obj, "__len__") and (isinstance(obj, Batch) or obj.ndim > 0): lens.append(len(obj)) else: raise TypeError(f"Object {obj} in {self} has no len()") - if len(lens) == 0: - # empty batch has the shape of any, like the tensorflow '?' shape. - # So it has no length. - raise TypeError(f"Object {self} has no len()") + if not lens: + return 0 return min(lens) def is_empty(self, recurse: bool = False) -> bool: