Beispiel #1
0
void
aubio_pitchspecacf_do (aubio_pitchspecacf_t * p, const fvec_t * input, fvec_t * output)
{
    uint_t l, tau;
    fvec_t *fftout = p->fftout;
    // window the input
    for (l = 0; l < input->length; l++) {
        p->winput->data[l] = p->win->data[l] * input->data[l];
    }
    // get the real / imag parts of its fft
    aubio_fft_do_complex (p->fft, p->winput, fftout);
    for (l = 0; l < input->length / 2 + 1; l++) {
        p->sqrmag->data[l] = SQR(fftout->data[l]);
    }
    // get the real / imag parts of the fft of the squared magnitude
    aubio_fft_do_complex (p->fft, p->sqrmag, fftout);
    // copy real part to acf
    for (l = 0; l < fftout->length / 2 + 1; l++) {
        p->acf->data[l] = fftout->data[l];
    }
    // get the minimum
    tau = fvec_min_elem (p->acf);
    // get the interpolated minimum
    output->data[0] = fvec_quadratic_peak_pos (p->acf, tau) * 2.;
}
/* all the above in one */
void
aubio_pitchyin_do (aubio_pitchyin_t * o, fvec_t * input, fvec_t * out)
{
  smpl_t tol = o->tol;
  fvec_t *yin = o->yin;
  uint_t j, tau = 0;
  sint_t period;
  smpl_t tmp = 0., tmp2 = 0.;
  yin->data[0] = 1.;
  for (tau = 1; tau < yin->length; tau++) {
    yin->data[tau] = 0.;
    for (j = 0; j < yin->length; j++) {
      tmp = input->data[j] - input->data[j + tau];
      yin->data[tau] += SQR (tmp);
    }
    tmp2 += yin->data[tau];
    yin->data[tau] *= tau / tmp2;
    period = tau - 3;
    if (tau > 4 && (yin->data[period] < tol) &&
        (yin->data[period] < yin->data[period + 1])) {
      out->data[0] = fvec_quadratic_peak_pos (yin, period);
      goto beach;
    }
  }
  out->data[0] = fvec_quadratic_peak_pos (yin, fvec_min_elem (yin));
beach:
  return;
}
Beispiel #3
0
void
aubio_pitchyinfft_do (aubio_pitchyinfft_t * p, fvec_t * input, fvec_t * output)
{
  uint_t tau, l;
  uint_t halfperiod;
  smpl_t tmp, sum;
  cvec_t *res = (cvec_t *) p->res;
  fvec_t *yin = (fvec_t *) p->yinfft;
  l = 0;
  tmp = 0.;
  sum = 0.;
  for (l = 0; l < input->length; l++) {
    p->winput->data[l] = p->win->data[l] * input->data[l];
  }
  aubio_fft_do (p->fft, p->winput, p->fftout);
  for (l = 0; l < p->fftout->length; l++) {
    p->sqrmag->data[l] = SQR (p->fftout->norm[l]);
    p->sqrmag->data[l] *= p->weight->data[l];
  }
  for (l = 1; l < p->fftout->length; l++) {
    p->sqrmag->data[(p->fftout->length - 1) * 2 - l] =
        SQR (p->fftout->norm[l]);
    p->sqrmag->data[(p->fftout->length - 1) * 2 - l] *=
        p->weight->data[l];
  }
  for (l = 0; l < p->sqrmag->length / 2 + 1; l++) {
    sum += p->sqrmag->data[l];
  }
  sum *= 2.;
  aubio_fft_do (p->fft, p->sqrmag, res);
  yin->data[0] = 1.;
  for (tau = 1; tau < yin->length; tau++) {
    yin->data[tau] = sum - res->norm[tau] * COS (res->phas[tau]);
    tmp += yin->data[tau];
    yin->data[tau] *= tau / tmp;
  }
  tau = fvec_min_elem (yin);
  if (yin->data[tau] < p->tol) {
    /* no interpolation */
    //return tau;
    /* 3 point quadratic interpolation */
    //return fvec_quadint_min(yin,tau,1);
    /* additional check for (unlikely) octave doubling in higher frequencies */
    if (tau > 35) {
      output->data[0] = fvec_quadint (yin, tau);
    } else {
      /* should compare the minimum value of each interpolated peaks */
      halfperiod = FLOOR (tau / 2 + .5);
      if (yin->data[halfperiod] < p->tol)
        output->data[0] = fvec_quadint (yin, halfperiod);
      else
        output->data[0] = fvec_quadint (yin, tau);
    }
  } else {
    output->data[0] = 0.;
  }
}
Beispiel #4
0
void
aubio_pitchyinfft_do (aubio_pitchyinfft_t * p, fvec_t * input, fvec_t * output)
{
  uint_t tau, l;
  uint_t length = p->fftout->length;
  uint_t halfperiod;
  fvec_t *fftout = p->fftout;
  fvec_t *yin = p->yinfft;
  smpl_t tmp = 0., sum = 0.;
  // window the input
  for (l = 0; l < input->length; l++) {
    p->winput->data[l] = p->win->data[l] * input->data[l];
  }
  // get the real / imag parts of its fft
  aubio_fft_do_complex (p->fft, p->winput, fftout);
  // get the squared magnitude spectrum, applying some weight
  p->sqrmag->data[0] = SQR(fftout->data[0]);
  p->sqrmag->data[0] *= p->weight->data[0];
  for (l = 1; l < length / 2; l++) {
    p->sqrmag->data[l] = SQR(fftout->data[l]) + SQR(fftout->data[length - l]);
    p->sqrmag->data[l] *= p->weight->data[l];
    p->sqrmag->data[length - l] = p->sqrmag->data[l];
  }
  p->sqrmag->data[length / 2] = SQR(fftout->data[length / 2]);
  p->sqrmag->data[length / 2] *= p->weight->data[length / 2];
  // get sum of weighted squared mags
  for (l = 0; l < length / 2 + 1; l++) {
    sum += p->sqrmag->data[l];
  }
  sum *= 2.;
  // get the real / imag parts of the fft of the squared magnitude
  aubio_fft_do_complex (p->fft, p->sqrmag, fftout);
  yin->data[0] = 1.;
  for (tau = 1; tau < yin->length; tau++) {
    // compute the square differences
    yin->data[tau] = sum - fftout->data[tau];
    // and the cumulative mean normalized difference function
    tmp += yin->data[tau];
    if (tmp != 0) {
      yin->data[tau] *= tau / tmp;
    } else {
      yin->data[tau] = 1.;
    }
  }
  // find best candidates
  tau = fvec_min_elem (yin);
  if (yin->data[tau] < p->tol) {
    // no interpolation, directly return the period as an integer
    //output->data[0] = tau;
    //return;

    // 3 point quadratic interpolation
    //return fvec_quadratic_peak_pos (yin,tau,1);
    /* additional check for (unlikely) octave doubling in higher frequencies */
    if (tau > p->short_period) {
      output->data[0] = fvec_quadratic_peak_pos (yin, tau);
    } else {
      /* should compare the minimum value of each interpolated peaks */
      halfperiod = FLOOR (tau / 2 + .5);
      if (yin->data[halfperiod] < p->tol)
        output->data[0] = fvec_quadratic_peak_pos (yin, halfperiod);
      else
        output->data[0] = fvec_quadratic_peak_pos (yin, tau);
    }
  } else {
    output->data[0] = 0.;
  }
}