class_docstr: This class calculates Viterbi alignments in the forward method.
  
  It also records alignments and creates batches of them for use
  in Viterbi training.
  
  Arguments
  ---------
  states_per_phoneme : int
      Number of hidden states to use per phoneme.
  output_folder : str
      It is the folder that the alignments will be stored in when
      saved to disk. Not yet implemented.
  neg_inf : float
      The float used to represent a negative infinite log probability.
      Using `-float("Inf")` tends to give numerical instability.
      A number more negative than -1e5 also sometimes gave errors when
      the `genbmm` library was used (currently not in use). (default: -1e5)
  batch_reduction : string
      One of "none", "sum" or "mean".
      What kind of batch-level reduction to apply to the loss calculated
      in the forward method.
  input_len_norm : bool
      Whether to normalize the loss in the forward method by the length of
      the inputs.
  target_len_norm : bool
      Whether to normalize the loss in the forward method by the length of
      the targets.
  lexicon_path : string
      The location of the lexicon.
  
  Example
  -------
  >>> log_posteriors = torch.tensor([[[ -1., -10., -10.],
  ...                                 [-10.,  -1., -10.],
  ...                                 [-10., -10.,  -1.]],
  ...
  ...                                [[ -1., -10., -10.],
  ...                                 [-10.,  -1., -10.],
  ...                                 [-10., -10., -10.]]])
  >>> lens = torch.tensor([1., 0.66])
  >>> phns = torch.tensor([[0, 1, 2],
  ...                      [0, 1, 0]])
  >>> phn_lens = torch.tensor([1., 0.66])
  >>> aligner = HMMAligner()
  >>> forward_scores = aligner(
  ...        log_posteriors, lens, phns, phn_lens, 'forward'
  ... )
  >>> forward_scores.shape
  torch.Size([2])
  >>> viterbi_scores, alignments = aligner(
  ...        log_posteriors, lens, phns, phn_lens, 'viterbi'
  ... )
  >>> alignments
  [[0, 1, 2], [0, 1]]
  >>> viterbi_scores.shape
  torch.Size([2])
docstr: Expands each phoneme in the phn sequence by the number of hidden
  states per phoneme defined in the HMM.
  
  Arguments
  ---------
  phns : torch.Tensor (batch, phoneme in phn sequence)
      The phonemes that are known/thought to be in each utterance.
  phn_lens : torch.Tensor (batch)
      The relative length of each phoneme sequence in the batch.
  
  Returns
  -------
  expanded_phns : torch.Tensor (batch, phoneme in expanded phn sequence)
  
  Example
  -------
  >>> phns = torch.tensor([[0., 3., 5., 0.],
  ...                      [0., 2., 0., 0.]])
  >>> phn_lens = torch.tensor([1., 0.75])
  >>> aligner = HMMAligner(states_per_phoneme = 3)
  >>> expanded_phns = aligner.expand_phns_by_states_per_phoneme(
  ...         phns, phn_lens
  ... )
  >>> expanded_phns
  tensor([[ 0.,  1.,  2.,  9., 10., 11., 15., 16., 17.,  0.,  1.,  2.],
          [ 0.,  1.,  2.,  6.,  7.,  8.,  0.,  1.,  2.,  0.,  0.,  0.]])
docstr_tok: ["Expands","each","phoneme","in","the","phn","sequence","by","the","number","of","hidden","states","per","phoneme","defined","in","the","HMM",".","Arguments","--","--","--","--","-","phns",":","torch.Tensor","(","batch",",","phoneme","in","phn","sequence",")","The","phonemes","that","are","known\/thought","to","be","in","each","utterance",".","phn_lens",":","torch.Tensor","(","batch",")","The","relative","length","of","each","phoneme","sequence","in","the","batch",".","Returns","--","--","--","-","expanded_phns",":","torch.Tensor","(","batch",",","phoneme","in","expanded","phn","sequence",")","Example","--","--","--","-",">",">",">","phns","=","torch.tensor","(","[","[","0.",",","3.",",","5.",",","0",".","]",",","...","[","0.",",","2.",",","0.",",","0",".","]","]",")",">",">",">","phn_lens","=","torch.tensor","(","[","1.",",","0.75","]",")",">",">",">","aligner","=","HMMAligner","(","states_per_phoneme","=","3",")",">",">",">","expanded_phns","=","aligner.expand_phns_by_states_per_phoneme","(","...","phns",",","phn_lens","...",")",">",">",">","expanded_phns","tensor","(","[","[","0.",",","1.",",","2.",",","9.",",","10.",",","11.",",","15.",",","16.",",","17.",",","0.",",","1.",",","2",".","]",",","[","0.",",","1.",",","2.",",","6.",",","7.",",","8.",",","0.",",","1.",",","2.",",","0.",",","0.",",","0",".","]","]",")"]
code: def expand_phns_by_states_per_phoneme(self, phns, phn_lens):
      """Expands each phoneme in the phn sequence by the number of hidden
      states per phoneme defined in the HMM.
  
      Arguments
      ---------
      phns : torch.Tensor (batch, phoneme in phn sequence)
          The phonemes that are known/thought to be in each utterance.
      phn_lens : torch.Tensor (batch)
          The relative length of each phoneme sequence in the batch.
  
      Returns
      -------
      expanded_phns : torch.Tensor (batch, phoneme in expanded phn sequence)
  
      Example
      -------
      >>> phns = torch.tensor([[0., 3., 5., 0.],
      ...                      [0., 2., 0., 0.]])
      >>> phn_lens = torch.tensor([1., 0.75])
      >>> aligner = HMMAligner(states_per_phoneme = 3)
      >>> expanded_phns = aligner.expand_phns_by_states_per_phoneme(
      ...         phns, phn_lens
      ... )
      >>> expanded_phns
      tensor([[ 0.,  1.,  2.,  9., 10., 11., 15., 16., 17.,  0.,  1.,  2.],
              [ 0.,  1.,  2.,  6.,  7.,  8.,  0.,  1.,  2.,  0.,  0.,  0.]])
      """
      # Initialise expanded_phns
      expanded_phns = torch.zeros(
          phns.shape[0], phns.shape[1] * self.states_per_phoneme
      )
      expanded_phns = expanded_phns.to(phns.device)
  
      phns = undo_padding(phns, phn_lens)
      for i, phns_utt in enumerate(phns):
          expanded_phns_utt = []
          for phoneme_index in phns_utt:
              expanded_phns_utt += [
                  self.states_per_phoneme * phoneme_index + i_
                  for i_ in range(self.states_per_phoneme)
              ]
  
          expanded_phns[i, : len(expanded_phns_utt)] = torch.tensor(
              expanded_phns_utt
          )
      return expanded_phns
  
imports: import torch
  import random
  from speechbrain.utils.checkpoints import register_checkpoint_hooks
  from speechbrain.utils.checkpoints import mark_as_saver
  from speechbrain.utils.checkpoints import mark_as_loader
  from speechbrain.utils.data_utils import undo_padding
label_desc: Use image node_id 11 for calling the HMMAligner obj's underlying member method code with example usage: obj.expand_phns_by_states_per_phoneme(phns, phn_lens) and returns: expanded_phns