Bitcasts `self` to the given `dtype` of the same itemsize. ```python exec="true" source="above" session="tensor" result="python" t = Tensor([-1, 2, 3], dtype=dtypes.int32) print(t.dtype, t.numpy()) ``` ```python exec="true" source="above" session="tensor" result="python"
(self, dtype:DTypeLike)
| 1404 | return self if self.dtype == (dt:=to_dtype(dtype)) else self._apply_uop(UOp.cast, dtype=dt) |
| 1405 | |
| 1406 | def bitcast(self, dtype:DTypeLike) -> Tensor: |
| 1407 | """ |
| 1408 | Bitcasts `self` to the given `dtype` of the same itemsize. |
| 1409 | |
| 1410 | ```python exec="true" source="above" session="tensor" result="python" |
| 1411 | t = Tensor([-1, 2, 3], dtype=dtypes.int32) |
| 1412 | print(t.dtype, t.numpy()) |
| 1413 | ``` |
| 1414 | ```python exec="true" source="above" session="tensor" result="python" |
| 1415 | t = t.bitcast(dtypes.uint32) |
| 1416 | print(t.dtype, t.numpy()) |
| 1417 | ``` |
| 1418 | """ |
| 1419 | dt = to_dtype(dtype) |
| 1420 | if (ns:=dt.itemsize) != (os:=self.dtype.itemsize) and (self.shape[-1]*os) % ns != 0: raise RuntimeError("unsupported size in bitcast") |
| 1421 | if (not isinstance(self.device, str) or not self.device.startswith("DISK")) and ns != os: |
| 1422 | new_uint, old_uint = to_dtype(f"uint{8*ns}"), to_dtype(f"uint{8*os}") |
| 1423 | tmp = self.bitcast(old_uint) |
| 1424 | if ns > os: |
| 1425 | tmp = tmp.reshape(self.shape[:-1] + (self.shape[-1]//(rate := ns//os), rate)) |
| 1426 | nones = (None,) * (tmp.ndim - 1) |
| 1427 | return Tensor.usum(*[tmp.shrink(nones + ((i, i+1),)).cast(new_uint)<<8*i*os for i in range(rate)]).squeeze(-1).bitcast(dtype) |
| 1428 | return Tensor.stack(*(tmp>>8*i*ns for i in range(os//ns)), dim=-1).flatten(-2).cast(new_uint).bitcast(dtype) |
| 1429 | return self._apply_uop(UOp.bitcast, dtype=dt) if self.dtype != dt else self |
| 1430 | |
| 1431 | # *** image Tensor function replacements *** |
| 1432 |