class_docstr: Represents a full generative context-free grammar with
  non-terminals NT and terminals T.
  
  Event shape is of the form:
  
  Parameters:
      log_potentials (tuple) : event tuple with event shapes
                       terms (*N x T*)
                       rules (*NT x (NT+T) x (NT+T)*)
                       root  (*NT*)
      lengths (long tensor) : batch shape integers for length masking.
  
  Implementation uses width-batched, forward-pass only
  
  * Parallel Time: :math:`O(N)` parallel merges.
  * Forward Memory: :math:`O(N^2 (NT+T))`
  
  Compact representation:  (*N x N x NT*) long tensor
code: def __init__(self, log_potentials, lengths=None, validate_args=False):
      batch_shape = log_potentials[0].shape[:1]
      event_shape = log_potentials[0].shape[1:]
      self.log_potentials = log_potentials
      self.lengths = lengths
      super(StructDistribution, self).__init__(
          batch_shape=batch_shape,
          event_shape=event_shape,
          validate_args=validate_args,
      )
  
imports: import torch
  from torch.distributions import constraints
  from torch.distributions.distribution import Distribution
  from torch.distributions.utils import lazy_property
  from .linearchain import LinearChain
  from .cky import CKY
  from .semimarkov import SemiMarkov
  from .alignment import Alignment
  from .deptree import DepTree, deptree_nonproj, deptree_part
  from .cky_crf import CKY_CRF
  from .semirings import LogSemiring, MaxSemiring, EntropySemiring, CrossEntropySemiring, KLDivergenceSemiring, MultiSampledSemiring, KMaxSemiring, StdSemiring, GumbelCRFSemiring
label_desc: Use image node_id 1 to create a new SentCFG object from inherited base classes: StructDistribution with example: obj = SentCFG(log_potentials, lengths, validate_args)