class_docstr: A single rasterized attribute and optionally its screen-space derivatives.
  
  Tensors are expected to have shape [batch, height, width, channels] or
  [batch, num_layers, height, width, channels].
  
  Immutable once created.
class_docstr_tok: ["A","single","rasterized","attribute","and","optionally","its","screen-space","derivatives",".","Tensors","are","expected","to","have","shape","[","batch",",","height",",","width",",","channels","]","or","[","batch",",","num_layers",",","height",",","width",",","channels","]",".","Immutable","once","created","."]
code: def __post_init__(self):
      # Checks that all input tensors have the same shape and rank.
      tensors = [self.value, self.d_dx, self.d_dy]
      shapes = [
          tensor.shape.as_list()
          for tensor in tensors
          if tensor is not None
      ]
      ranks = [len(shape) for shape in shapes]
      if not all(rank == ranks[0] for rank in ranks):
          raise ValueError(
              "Expected value and derivatives to be of the same rank, but found"
              f" ranks {shapes}"
          )
  
      value_rank = len(self.value.shape)
      if value_rank not in (4, 5):
          raise ValueError(
              f"Expected input value to be rank 4 or 5, but is {value_rank}"
          )
  
      same_as_value = True
      static_shapes = [self.value.shape]
      d_dx = self.d_dx
      if d_dx is not None:
          same_as_value = tf.logical_and(
              same_as_value,
              tf.equal(tf.shape(self.value), tf.shape(d_dx)),
          )
          static_shapes.append(d_dx.shape)
      d_dy = self.d_dy
      if d_dy is not None:
          same_as_value = tf.logical_and(
              same_as_value,
              tf.equal(tf.shape(self.value), tf.shape(d_dy)),
          )
          static_shapes.append(d_dy.shape)
      tf.debugging.assert_equal(
          same_as_value,
          True,
          message="Expected all input shapes to be the same but found: "
          + ", ".join([str(s) for s in static_shapes]),
      )
  
file_path: graphics/tensorflow_graphics/rendering/framebuffer.py
imports: import dataclasses
  from typing import Dict, Optional
  import tensorflow
label_desc: Use image node_id 1 for calling the RasterizedAttribute obj's underlying member method code with example usage: obj.__post_init__() without return types