def _unstack_once(
        self,
        index: pd.MultiIndex,
        dim: Hashable,
        fill_value=dtypes.NA,
        sparse: bool = False,
    ) -> Variable:
        """
        Unstacks this variable given an index to unstack and the name of the
        dimension to which the index refers.
        """

        reordered = self.transpose(..., dim)

        new_dim_sizes = [lev.size for lev in index.levels]
        new_dim_names = index.names
        indexer = index.codes

        # Potentially we could replace `len(other_dims)` with just `-1`
        other_dims = [d for d in self.dims if d != dim]
        new_shape = tuple(list(reordered.shape[: len(other_dims)]) + new_dim_sizes)
        new_dims = reordered.dims[: len(other_dims)] + tuple(new_dim_names)

        create_template: Callable
        if fill_value is dtypes.NA:
            is_missing_values = math.prod(new_shape) > math.prod(self.shape)
            if is_missing_values:
                dtype, fill_value = dtypes.maybe_promote(self.dtype)

                create_template = partial(
                    duck_array_ops.full_like, fill_value=fill_value
                )
            else:
                dtype = self.dtype
                fill_value = dtypes.get_fill_value(dtype)
                create_template = duck_array_ops.empty_like
        else:
            dtype = self.dtype
            create_template = partial(duck_array_ops.full_like, fill_value=fill_value)

        if sparse:
            # unstacking a dense multitindexed array to a sparse array
            from sparse import COO

            codes = zip(*index.codes, strict=True)
            if reordered.ndim == 1:
                indexes = codes
            else:
                sizes = itertools.product(*[range(s) for s in reordered.shape[:-1]])
                tuple_indexes = itertools.product(sizes, codes)
                indexes = (list(itertools.chain(*x)) for x in tuple_indexes)  # type: ignore[assignment]

            data = COO(
                coords=np.array(list(indexes)).T,
                data=self.data.astype(dtype).ravel(),
                fill_value=fill_value,
                shape=new_shape,
                sorted=index.is_monotonic_increasing,
            )

        else:
            data = create_template(self.data, shape=new_shape, dtype=dtype)

            # Indexer is a list of lists of locations. Each list is the locations
            # on the new dimension. This is robust to the data being sparse; in that
            # case the destinations will be NaN / zero.
            data[(..., *indexer)] = reordered

        return self.to_base_variable()._replace(dims=new_dims, data=data)

        Unstacks this variable given an index to unstack and the name of the
        dimension to which the index refers.
        
xarray/core/variable.py