jax-ml/jax · error · TypeError

len() of unsized object

Error message

len() of unsized object

What it means

ShapedArray._len mimics NumPy: calling len() on a 0-d (scalar) array-like aval has no first dimension, so shape[0] raises IndexError which is re-raised as TypeError('len() of unsized object').

Source

Thrown at jax/_src/core.py:2584

  def to_tangent_aval(self):
    return ShapedArray._create(
        self.shape, primal_dtype_to_tangent_dtype(self.dtype),
        self.weak_type, self.sharding, self.mat, self.memory_space,
        self.layout)

  def to_ct_aval(self):
    dtype = primal_dtype_to_tangent_dtype(self.dtype)
    sharding = primal_sharding_to_cotangent_sharding(self.sharding)
    ct_mat = self.mat.to_ct_mat()
    return ShapedArray._create(
        self.shape, dtype, self.weak_type, sharding, ct_mat, self.memory_space,
        self.layout)

  def _len(self, ignored_tracer):
    try:
      return self.shape[0]
    except IndexError as err:
      raise TypeError("len() of unsized object") from err  # same as numpy error

  def update_manual_axis_type(self, mat):
    mat = get_mat(mat, self.sharding.mesh)
    if mat is self.manual_axis_type:
      return self
    return ShapedArray._create(self.shape, self.dtype, self.weak_type,
                               self.sharding, mat, self.memory_space,
                               self.layout)

  def update_weak_type(self, weak_type):
    if weak_type == self.weak_type:
      return self
    return ShapedArray._create(self.shape, self.dtype, weak_type, self.sharding,
                               self.manual_axis_type, self.memory_space,
                               self.layout)

  def strip_weak_type(self) -> AbstractValue:
    if not self.weak_type:

View on GitHub (pinned to 1e1c6a8fc0)

Solutions

  1. Check x.ndim > 0 (or x.shape) before calling len
  2. Use x.shape[0] guarded, or restructure so scalars take a different branch
  3. Audit squeeze()/reduction calls producing 0-d results

Example fix

// before
def f(x):
    n = len(x)  # fails when x is scalar

// after
def f(x):
    n = x.shape[0] if x.ndim else 1
Defensive patterns

Strategy: type-guard

Validate before calling

if arr.ndim == 0:
    raise TypeError('scalar has no len')

Type guard

def has_len(x): return getattr(getattr(x, 'ndim', None), '__gt__', lambda _: False)(0)

Try / catch

try:
    n = len(x)
except TypeError:
    n = 1  # scalar

Prevention

When it happens

Trigger: len(x) where x is a 0-dimensional tracer/aval, e.g. inside jit on a scalar from jax.random.randint((), ...) or a scalar loss value.

Common situations: Generic code doing len(batch) that also receives scalars; data pipelines where a tensor unexpectedly collapses to 0-d after squeeze/reduction.

Related errors


AI-assisted analysis of jax-ml/jax@1e1c6a8fc0 (2026-08-27). Data as JSON: /api/errors/95a9e7baf6d4a693. Report an issue: GitHub.