/** 
 * @brief  Compute a set of Gaussians with no pruning
 *
 * The calculated scores will be stored to OP_calced_score, with its
 * corresponding mixture id to OP_calced_id. 
 * The number of calculated mixtures is also stored in OP_calced_num.
 * 
 * This can be called from calc_tied_mix() or calc_mix().
 * 
 * @param wrk [i/o] HMM computation work area
 * @param g [in] set of Gaussian densities to compute the output probability.
 * @param num [in] length of above
 * @param last_id [in] ID list of N-best mixture in previous input frame,
 * or NULL if not exist
 * @param lnum [in] length of last_id
 */
void
gprune_none(HMMWork *wrk, HTK_HMM_Dens **g, int num, int *last_id, int lnum)
{
  int i;
  HTK_HMM_Dens *dens;
  LOGPROB *prob = wrk->OP_calced_score;
  int *id = wrk->OP_calced_id;
#ifdef ENABLE_MSD
  int valid_dim;
  int calced_num;
#endif

#ifdef ENABLE_MSD

  valid_dim = 0;
  for(i=0; i<wrk->OP_veclen; i++) {
    if (wrk->OP_vec[i] != LZERO) valid_dim++;
  }
  calced_num = 0;
  for(i=0; i<num; i++) {
    dens = *(g++);
    if (dens->meanlen != valid_dim) continue;
    if (dens->meanlen == 0) {
      *(prob++) = 0.0;
    } else {
      *(prob++) = compute_g_base(wrk, dens);
    }
    *(id++) = i;
    calced_num++;
  }
  if (calced_num == 0) {
    jlog("Error: MSD: input data dim = %d / %d, but no Gaussian defined for it\n", valid_dim, wrk->OP_veclen);
    jlog("Error: MSD: Gaussian dimensions in this mixture:");
    for(i=0;i<num;i++) {
      jlog(" %d", g[i]->meanlen);
    }
    jlog("\n");
  }
  wrk->OP_calced_num = calced_num;

#else

  for(i=0; i<num; i++) {
    dens = *(g++);
    *(prob++) = compute_g_base(wrk, dens);
    *(id++) = i;
  }
  wrk->OP_calced_num = num;

#endif
}
Example #2
0
/** 
 * @brief  Compute a set of Gaussians with safe pruning.
 *
 * If the N-best mixtures in the previous frame is specified in @a last_id,
 * They are first computed to set the initial threshold.
 * After that, the rest of the Gaussians will be computed with the thresholds
 * to drop unpromising Gaussians from computation at early stage
 * of likelihood computation.  If the computation of a Gaussian reached to
 * the end, the threshold will be updated to always hold the likelihood of
 * current N-best score.
 *
 * The calculated scores will be stored to OP_calced_score, with its
 * corresponding mixture id to OP_calced_id.  These are done by calling
 * cache_push().
 * The number of calculated mixtures is also stored in OP_calced_num.
 * 
 * This can be called from calc_tied_mix() or calc_mix().
 * 
 * @param wrk [i/o] HMM computation work area
 * @param g [in] set of Gaussian densities to compute the output probability
 * @param gnum [in] length of above
 * @param last_id [in] ID list of N-best mixture in previous input frame,
 * or NULL if not exist
 * @param lnum [in] length of last_id
 */
void
gprune_safe(HMMWork *wrk, HTK_HMM_Dens **g, int gnum, int *last_id, int lnum)
{
  int i, j, num = 0;
  LOGPROB score, thres;

  if (last_id != NULL) {	/* compute them first to form threshold */
    /* 1. calculate first $OP_gprune_num and set initial threshold */
    for (j=0; j<lnum; j++) {
      i = last_id[j];
      score = compute_g_base(wrk, g[i]);
      num = cache_push(wrk, i, score, num);
      wrk->mixcalced[i] = TRUE;      /* mark them as calculated */
    }
    thres = wrk->OP_calced_score[num-1];
    /* 2. calculate the rest with pruning*/
    for (i = 0; i < gnum; i++) {
      /* skip calced ones in 1. */
      if (wrk->mixcalced[i]) {
        wrk->mixcalced[i] = FALSE;
        continue;
      }
      /* compute with safe pruning */
      score = compute_g_safe(wrk, g[i], thres);
      if (score <= thres) continue;
      num = cache_push(wrk, i, score, num);
      thres = wrk->OP_calced_score[num-1];
    }
  } else {			/* in case the last_id not available */
    /* not tied-mixture, or at the first 0 frame */
    thres = LOG_ZERO;
    for (i = 0; i < gnum; i++) {
      if (num < wrk->OP_gprune_num) {
	score = compute_g_base(wrk, g[i]);
      } else {
	score = compute_g_safe(wrk, g[i], thres);
	if (score <= thres) continue;
      }
      num = cache_push(wrk, i, score, num);
      thres = wrk->OP_calced_score[num-1];
    }
  }
  wrk->OP_calced_num = num;
}
Example #3
0
/** 
 * @brief  Compute a set of Gaussians with heuristic pruning.
 *
 * If the N-best mixtures in the previous frame is specified in @a last_id,
 * They are first computed to get the maximum value for each dimension.
 * After that, the rest of the Gaussians will be computed using the maximum
 * values as heuristics of uncomputed dimensions to drop unpromising
 * Gaussians from computation at early stage
 * of likelihood computation.  If the @a last_id is not specified (typically
 * at the first frame of the input), a safe pruning as same as one in
 * gprune_safe.c will be applied.
 *
 * The calculated scores will be stored to OP_calced_score, with its
 * corresponding mixture id to OP_calced_id.  These are done by calling
 * cache_push().
 * The number of calculated mixtures is also stored in OP_calced_num.
 * 
 * This can be called from calc_tied_mix() or calc_mix().
 * 
 * @param wrk [i/o] HMM computation work area
 * @param g [in] set of Gaussian densities to compute the output probability
 * @param gnum [in] length of above
 * @param last_id [in] ID list of N-best mixture in previous input frame,
 * or NULL if not exist
 * @param lnum [in] length of last_id
 */
void
gprune_heu(HMMWork *wrk, HTK_HMM_Dens **g, int gnum, int *last_id, int lnum)
{
  int i, j, num = 0;
  LOGPROB score, thres;

  if (last_id != NULL) {	/* compute them first to form thresholds */
    /* 1. clear backmax */
    init_backmax(wrk);
    /* 2. calculate first $OP_gprune_num with setting max for each dimension */
    for (j=0; j<lnum; j++) {
      i = last_id[j];
      score = compute_g_heu_updating(wrk, g[i]);
      num = cache_push(wrk, i, score, num);
      wrk->mixcalced[i] = TRUE;      /* mark them as calculated */
    }
    /* 3. set backmax for each dimension */
    make_backmax(wrk);
    /* 4. calculate the rest with pruning*/
    thres = wrk->OP_calced_score[num-1];
    for (i = 0; i < gnum; i++) {
      /* skip calced ones in 1. */
      if (wrk->mixcalced[i]) {
        wrk->mixcalced[i] = FALSE;
        continue;
      }
      /* compute with safe pruning */
      score = compute_g_heu_pruning(wrk, g[i], thres);
      if (score > LOG_ZERO) {
	num = cache_push(wrk, i, score, num);
	thres = wrk->OP_calced_score[num-1];
      }
    }
  } else {			/* in case the last_id not available */
    /* at the first 0 frame */
    /* calculate with safe pruning */
    thres = LOG_ZERO;
    for (i = 0; i < gnum; i++) {
      if (num < wrk->OP_gprune_num) {
	score = compute_g_base(wrk, g[i]);
      } else {
	score = compute_g_safe(wrk, g[i], thres);
	if (score <= thres) continue;
      }
      num = cache_push(wrk, i, score, num);
      thres = wrk->OP_calced_score[num-1];
    }
  }
  wrk->OP_calced_num = num;
}
Example #4
0
/** 
 * Main function to compute all the GMS %HMM states in a frame
 * with the input vectore specified by OP_vec.  This function assumes
 * that this will be called for sequencial frame, since it utilizes the
 * result of previous frame for faster pruning.
 * 
 * @param wrk [i/o] HMM computation work area
 * 
 */
void
compute_gs_scores(HMMWork *wrk)
{
  int i;

  for (i=0;i<wrk->gsset_num;i++) {
#ifdef GS_MAX_PROB
#ifdef LAST_BEST
    /* compute only the maximum with pruning (last best first) */
    wrk->t_fs[i] = compute_g_max(wrk, wrk->gsset[i].state, wrk->gms_last_max_id_list[i]);
#else
    wrk->t_fs[i] = compute_g_max(wrk, wrk->gsset[i].state);
#endif /* LAST_BEST */
#else
    /* compute all mixture */
    wrk->t_fs[i] = compute_g_base(wrk, wrk->gsset[i].state);
#endif
    /*printf("%d:%s:%f\n",i,gsset[i].book->name,t_fs[i]);*/
  }

}
Example #5
0
/** 
 * @brief  Compute a set of Gaussians with beam pruning.
 *
 * If the N-best mixtures in the previous frame is specified in @a last_id,
 * They are first computed to set the thresholds for each dimension.
 * After that, the rest of the Gaussians will be computed with those dimension
 * thresholds to drop unpromising Gaussians from computation at early stage
 * of likelihood computation.  If the @a last_id is not specified (typically
 * at the first frame of the input), a safe pruning as same as one in
 * gprune_safe.c will be applied.
 *
 * The calculated scores will be stored to OP_calced_score, with its
 * corresponding mixture id to OP_calced_id.  These are done by calling
 * cache_push().
 * The number of calculated mixtures is also stored in OP_calced_num.
 * 
 * This can be called from calc_tied_mix() or calc_mix().
 * 
 * @param wrk [i/o] HMM computation work area
 * @param g [in] set of Gaussian densities to compute the output probability
 * @param gnum [in] length of above
 * @param last_id [in] ID list of N-best mixture in previous input frame,
 * or NULL if not exist
 * @param lnum [in] length of last_id
 */
void
gprune_beam(HMMWork *wrk, HTK_HMM_Dens **g, int gnum, int *last_id, int lnum)
{
  int i, j, num = 0;
  LOGPROB score, thres;

  if (last_id != NULL) {	/* compute them first to form thresholds */
    /* 1. clear dimthres */
    clear_dimthres(wrk);
    /* 2. calculate first $OP_gprune_num and set initial thresholds */
    for (j=0; j<lnum; j++) {
      i = last_id[j];
#ifdef TEST2
      if (!g[i]) {
	score = LOG_ZERO;
      } else {
	score = compute_g_beam_updating(wrk, g[i]);
      }
      num = cache_push(wrk, i, score, num);
#else
      score = compute_g_beam_updating(wrk, g[i]);
      num = cache_push(wrk, i, score, num);
#endif
      wrk->mixcalced[i] = TRUE;      /* mark them as calculated */
    }
    /* 3. set pruning thresholds for each dimension */
    set_dimthres(wrk);

    /* 4. calculate the rest with pruning*/
    for (i = 0; i < gnum; i++) {
      /* skip calced ones in 1. */
      if (wrk->mixcalced[i]) {
        wrk->mixcalced[i] = FALSE;
        continue;
      }
#ifdef TEST2
      /* compute with safe pruning */
      if (!g[i]) continue;
      score = compute_g_beam_pruning(wrk, g[i]);
      if (score > LOG_ZERO) {
	num = cache_push(wrk, i, score, num);
      }
#else
      /* compute with safe pruning */
      score = compute_g_beam_pruning(wrk, g[i]);
      if (score > LOG_ZERO) {
	num = cache_push(wrk, i, score, num);
      }
#endif
    }
  } else {			/* in case the last_id not available */
    /* at the first 0 frame */
    /* calculate with safe pruning */
    thres = LOG_ZERO;
    for (i = 0; i < gnum; i++) {
      if (num < wrk->OP_gprune_num) {
	score = compute_g_base(wrk, g[i]);
      } else {
	score = compute_g_safe(wrk, g[i], thres);
	if (score <= thres) continue;
      }
      num = cache_push(wrk, i, score, num);
      thres = wrk->OP_calced_score[num-1];
    }
  }
  wrk->OP_calced_num = num;
}