class_docstr: This class additively combines a noise signal to the input signal.
  
  Arguments
  ---------
  csv_file : str
      The name of a csv file containing the location of the
      noise audio files. If none is provided, white noise will be used.
  csv_keys : list, None, optional
      Default: None . One data entry for the noise data should be specified.
      If None, the csv file is expected to have only one data entry.
  sorting : str
      The order to iterate the csv file, from one of the
      following options: random, original, ascending, and descending.
  num_workers : int
      Number of workers in the DataLoader (See PyTorch DataLoader docs).
  snr_low : int
      The low end of the mixing ratios, in decibels.
  snr_high : int
      The high end of the mixing ratios, in decibels.
  pad_noise : bool
      If True, copy noise signals that are shorter than
      their corresponding clean signals so as to cover the whole clean
      signal. Otherwise, leave the noise un-padded.
  start_index : int
      The index in the noise waveforms to start from. By default, chooses
      a random index in [0, len(noise) - len(waveforms)].
  normalize : bool
      If True, output noisy signals that exceed [-1,1] will be
      normalized to [-1,1].
  noise_funct: funct object
      function to use to draw a noisy sample. It is enabled if the csv files
      containing the noisy sequences are not provided. By default,
      torch.randn_like is used (to sample white noise). In general, it must
      be a function that takes in input the original waveform and returns
      a tensor with the corresponsing noise to add (e.g., see pink_noise_like).
  replacements : dict
      A set of string replacements to carry out in the
      csv file. Each time a key is found in the text, it will be replaced
      with the corresponding value.
  noise_sample_rate : int
      The sample rate of the noise audio signals, so noise can be resampled
      to the clean sample rate if necessary.
  clean_sample_rate : int
      The sample rate of the clean audio signals, so noise can be resampled
      to the clean sample rate if necessary.
  
  Example
  -------
  >>> import pytest
  >>> from speechbrain.dataio.dataio import read_audio
  >>> signal = read_audio('tests/samples/single-mic/example1.wav')
  >>> clean = signal.unsqueeze(0) # [batch, time, channels]
  >>> noisifier = AddNoise('tests/samples/annotation/noise.csv',
  ...                     replacements={'noise_folder': 'tests/samples/noise'})
  >>> noisy = noisifier(clean, torch.ones(1))
class_docstr_tok: ["This","class","additively","combines","a","noise","signal","to","the","input","signal",".","Arguments","--","--","--","--","-","csv_file",":","str","The","name","of","a","csv","file","containing","the","location","of","the","noise","audio","files",".","If","none","is","provided",",","white","noise","will","be","used",".","csv_keys",":","list",",","None",",","optional","Default",":","None",".","One","data","entry","for","the","noise","data","should","be","specified",".","If","None",",","the","csv","file","is","expected","to","have","only","one","data","entry",".","sorting",":","str","The","order","to","iterate","the","csv","file",",","from","one","of","the","following","options",":","random",",","original",",","ascending",",","and","descending",".","num_workers",":","int","Number","of","workers","in","the","DataLoader","(","See","PyTorch","DataLoader","docs",")",".","snr_low",":","int","The","low","end","of","the","mixing","ratios",",","in","decibels",".","snr_high",":","int","The","high","end","of","the","mixing","ratios",",","in","decibels",".","pad_noise",":","bool","If","True",",","copy","noise","signals","that","are","shorter","than","their","corresponding","clean","signals","so","as","to","cover","the","whole","clean","signal",".","Otherwise",",","leave","the","noise","un-padded",".","start_index",":","int","The","index","in","the","noise","waveforms","to","start","from",".","By","default",",","chooses","a","random","index","in","[","0",",","len","(","noise",")","-","len","(","waveforms",")","]",".","normalize",":","bool","If","True",",","output","noisy","signals","that","exceed","[","-1,1","]","will","be","normalized","to","[","-1,1","]",".","noise_funct",":","funct","object","function","to","use","to","draw","a","noisy","sample",".","It","is","enabled","if","the","csv","files","containing","the","noisy","sequences","are","not","provided",".","By","default",",","torch.randn_like","is","used","(","to","sample","white","noise",")",".","In","general",",","it","must","be","a","function","that","takes","in","input","the","original","waveform","and","returns","a","tensor","with","the","corresponsing","noise","to","add","(","e.g.",",","see","pink_noise_like",")",".","replacements",":","dict","A","set","of","string","replacements","to","carry","out","in","the","csv","file",".","Each","time","a","key","is","found","in","the","text",",","it","will","be","replaced","with","the","corresponding","value",".","noise_sample_rate",":","int","The","sample","rate","of","the","noise","audio","signals",",","so","noise","can","be","resampled","to","the","clean","sample","rate","if","necessary",".","clean_sample_rate",":","int","The","sample","rate","of","the","clean","audio","signals",",","so","noise","can","be","resampled","to","the","clean","sample","rate","if","necessary",".","Example","--","--","--","-",">",">",">","import","pytest",">",">",">","from","speechbrain.dataio.dataio","import","read_audio",">",">",">","signal","=","read_audio","(","'tests\/samples\/single-mic\/example1.wav","'",")",">",">",">","clean","=","signal.unsqueeze","(","0",")","#","[","batch",",","time",",","channels","]",">",">",">","noisifier","=","AddNoise","(","'tests\/samples\/annotation\/noise.csv","'",",","...","replacements=","{","'noise_folder","'",":","'tests\/samples\/noise","'","}",")",">",">",">","noisy","=","noisifier","(","clean",",","torch.ones","(","1",")",")"]
docstr: Load a batch of noises
docstr_tok: ["Load","a","batch","of","noises"]
code: def _load_noise(self, lengths, max_length):
      """Load a batch of noises"""
      lengths = lengths.long().squeeze(1)
      batch_size = len(lengths)
  
      # Load a noise batch
      if not hasattr(self, "data_loader"):
          if self.noise_sample_rate != self.clean_sample_rate:
              self.resampler = Resample(
                  self.noise_sample_rate, self.clean_sample_rate
              )
  
          # Set parameters based on input
          self.device = lengths.device
  
          # Create a data loader for the noise wavforms
          if self.csv_file is not None:
              dataset = ExtendedCSVDataset(
                  csvpath=self.csv_file,
                  output_keys=self.csv_keys,
                  sorting=self.sorting
                  if self.sorting != "random"
                  else "original",
                  replacements=self.replacements,
              )
              self.data_loader = make_dataloader(
                  dataset,
                  batch_size=batch_size,
                  num_workers=self.num_workers,
                  shuffle=(self.sorting == "random"),
              )
              self.noise_data = iter(self.data_loader)
  
      # Load noise to correct device
      noise_batch, noise_len = self._load_noise_batch_of_size(
          batch_size
      )
      noise_batch = noise_batch.to(lengths.device)
      noise_len = noise_len.to(lengths.device)
  
      # Resample noise if necessary
      if hasattr(self, "resampler"):
          noise_batch = self.resampler(noise_batch)
  
      # Convert relative length to an index
      noise_len = (noise_len * noise_batch.shape[1]).long()
  
      # Ensure shortest wav can cover speech signal
      # WARNING: THIS COULD BE SLOW IF THERE ARE VERY SHORT NOISES
      if self.pad_noise:
          while torch.any(noise_len < lengths):
              min_len = torch.min(noise_len)
              prepend = noise_batch[:, :min_len]
              noise_batch = torch.cat((prepend, noise_batch), axis=1)
              noise_len += min_len
  
      # Ensure noise batch is long enough
      elif noise_batch.size(1) < max_length:
          padding = (0, max_length - noise_batch.size(1))
          noise_batch = torch.nn.functional.pad(noise_batch, padding)
  
      # Select a random starting location in the waveform
      start_index = self.start_index
      if self.start_index is None:
          start_index = 0
          max_chop = (noise_len - lengths).min().clamp(min=1)
          start_index = torch.randint(
              high=max_chop, size=(1,), device=lengths.device
          )
  
      # Truncate noise_batch to max_length
      noise_batch = noise_batch[
          :, start_index : start_index + max_length
      ]
      noise_len = (
          (noise_len - start_index).clamp(max=max_length).unsqueeze(1)
      )
      return noise_batch, noise_len
  
imports: import math
  import random
  import torch
  import torch.nn.functional
  from speechbrain.dataio.legacy import ExtendedCSVDataset
  from speechbrain.dataio.dataloader import make_dataloader
  from speechbrain.processing.signal_processing import compute_amplitude, dB_to_amplitude, convolve1d, notch_filter, reverberate
label_desc: Use image node_id 3 for calling the AddNoise obj's underlying member method code with example usage: obj._load_noise(lengths, max_length) and returns: noise_batch,  noise_len