⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vithist.c

📁 CMU大名鼎鼎的SPHINX-3大词汇量连续语音识别系统
💻 C
📖 第 1 页 / 共 2 页
字号:
int32 vithist_utt_end (vithist_t *vh, kbcore_t *kbc){    int32 f, i, b, l;    int32 sv, nsv, scr, bestscore, bestvh, vhid;    vithist_entry_t *ve, *bestve=0;    s3lmwid_t endwid;    lm_t *lm;    dict_t *dict;    /* Find last frame with entries in vithist table */    for (f = vh->n_frm-1; f >= 0; --f) {	sv = vh->frame_start[f];	/* First vithist entry in frame f */	nsv = vh->frame_start[f+1];	/* First vithist entry in next frame (f+1) */		if (sv < nsv)	    break;    }    if (f < 0)	return -1;        if (f != vh->n_frm-1)	E_ERROR("No word exit in frame %d, using exits from frame %d\n", vh->n_frm-1, f);        /* Terminate in a final </s> node (make this optional?) */    lm = kbcore_lm (kbc);    endwid = lm_finishwid (lm);    dict = kbcore_dict (kbc);        bestscore = MAX_NEG_INT32;    bestvh = -1;        for (i = sv; i < nsv; i++) {	b = VITHIST_ID2BLK (i);	l = VITHIST_ID2BLKOFFSET (i);	ve = vh->entry[b] + l;		scr = ve->score;	scr += lm_tg_score (lm, ve->lmstate.lm3g.lwid[1], ve->lmstate.lm3g.lwid[0], endwid,dict_finishwid(dict));		if (bestscore < scr) {	    bestscore = scr;	    bestvh = i;	    bestve = ve;	}    }    assert (bestvh >= 0);        if (f != vh->n_frm-1) {	E_ERROR("No word exit in frame %d, using exits from frame %d\n", vh->n_frm-1, f);		/* Add a dummy silwid covering the remainder of the utterance */	assert (vh->frame_start[vh->n_frm-1] == vh->frame_start[vh->n_frm]);	vh->n_frm -= 1;	vithist_rescore (vh, kbc, dict_silwid (dict), vh->n_frm, bestve->score, bestvh, -1);	vh->n_frm += 1;	vh->frame_start[vh->n_frm] = vh->n_entry;		return vithist_utt_end (vh, kbc);    }        /* Create an </s> entry */    vhid = vh->n_entry;    ve = vithist_entry_alloc (vh);        ve->wid = dict_finishwid (dict);    ve->sf = (bestve->ef == BAD_S3FRMID) ? 0 : bestve->ef + 1;    ve->ef = vh->n_frm;    ve->ascr = 0;    ve->lscr = bestscore - bestve->score;    ve->score = bestscore;    ve->pred = bestvh;    ve->type = 0;    ve->valid = 1;    ve->lmstate.lm3g.lwid[0] = endwid;    ve->lmstate.lm3g.lwid[1] = ve->lmstate.lm3g.lwid[0];        return vhid;}int32 vithist_partialutt_end (vithist_t *vh, kbcore_t *kbc){    int32 f, i, b, l;    int32 sv, nsv, scr, bestscore, bestvh;    vithist_entry_t *ve, *bestve;    s3lmwid_t endwid;    lm_t *lm;    dict_t *dict;    /* Find last frame with entries in vithist table */    for (f = vh->n_frm-1; f >= 0; --f) {	sv = vh->frame_start[f];	/* First vithist entry in frame f */	nsv = vh->frame_start[f+1];	/* First vithist entry in next frame (f+1) */		if (sv < nsv)	    break;    }    if (f < 0)	return -1;        if (f != vh->n_frm-1){	E_ERROR("No word exits from in block with last frame= %d\n",vh->n_frm-1);	return -1;    }        /* Terminate in a final </s> node (make this optional?) */    lm = kbcore_lm (kbc);    dict = kbcore_dict (kbc);        endwid = lm_finishwid (lm);        bestscore = MAX_NEG_INT32;    bestvh = -1;        for (i = sv; i < nsv; i++) {	b = VITHIST_ID2BLK (i);	l = VITHIST_ID2BLKOFFSET (i);	ve = vh->entry[b] + l;		scr = ve->score;	scr += lm_tg_score (lm, ve->lmstate.lm3g.lwid[1], ve->lmstate.lm3g.lwid[0], endwid, dict_finishwid(dict));		if (bestscore < scr) {	    bestscore = scr;	    bestvh = i;	    bestve = ve;	}    }    return bestvh;}void vithist_utt_reset (vithist_t *vh){    int32 b;        vithist_lmstate_reset (vh);        for (b = VITHIST_ID2BLK(vh->n_entry-1); b >= 0; --b) {	ckd_free ((void *) vh->entry[b]);	vh->entry[b] = NULL;    }    vh->n_entry = 0;        vh->bestscore[0] = MAX_NEG_INT32;    vh->bestvh[0] = -1;}#if 0static void vithist_lmstate_subtree_dump (vithist_t *vh, kbcore_t *kbc,					  vh_lmstate2vithist_t *lms2vh, int32 level, FILE *fp){    gnode_t *gn;    vh_lmstate2vithist_t *child;    int32 i;    lm_t *lm;        lm = kbcore_lm (kbc);        for (gn = lms2vh->children; gn; gn = gnode_next(gn)) {	child = (vh_lmstate2vithist_t *) gnode_ptr (gn);		for (i = 0; i < level; i++)	    fprintf (fp, "\t");	fprintf (fp, "\t%s -> %d\n", lm_wordstr(lm, child->state), child->vhid);		vithist_lmstate_subtree_dump (vh, kbc, child, level+1, fp);    }}static void vithist_lmstate_dump (vithist_t *vh, kbcore_t *kbc, FILE *fp){    glist_t gl;    gnode_t *lgn, *gn;    int32 i;    vh_lmstate2vithist_t *lms2vh;    mdef_t *mdef;    lm_t *lm;        mdef = kbcore_mdef (kbc);    lm = kbcore_lm (kbc);        fprintf (fp, "LMSTATE\n");    for (lgn = vh->lwidlist; lgn; lgn = gnode_next(lgn)) {	i = (int32) gnode_int32 (lgn);		gl = vh->lmstate_root[i];	assert (gl);		for (gn = gl; gn; gn = gnode_next(gn)) {	    lms2vh = (vh_lmstate2vithist_t *) gnode_ptr (gn);	    	    fprintf (fp, "\t%s.%s -> %d\n",		     lm_wordstr(lm, i), mdef_ciphone_str (mdef, lms2vh->state), lms2vh->vhid);	    vithist_lmstate_subtree_dump (vh, kbc, lms2vh, 1, fp);	}    }    fprintf (fp, "END_LMSTATE\n");    fflush (fp);}#endifvoid vithist_dump (vithist_t *vh, int32 frm, kbcore_t *kbc, FILE *fp){    int32 b, l, i, j;    dict_t *dict;    lm_t *lm;    vithist_entry_t *ve;    s3lmwid_t lwid;    int32 sf, ef;        dict = kbcore_dict (kbc);    lm = kbcore_lm (kbc);        if (frm >= 0) {	sf = frm;	ef = frm;		fprintf (fp, "VITHIST  frame %d  #entries %d\n",		 frm, vh->frame_start[sf+1] - vh->frame_start[sf]);    } else {	sf = 0;	ef = vh->n_frm - 1;		fprintf (fp, "VITHIST  #frames %d  #entries %d\n", vh->n_frm, vh->n_entry);    }    fprintf (fp, "\t%7s %5s %5s %11s %9s %8s %7s %4s Word (LM-state)\n",	     "Seq/Val", "SFrm", "EFrm", "PathScr", "SegAScr", "SegLScr", "Pred", "Type");        for (i = sf; i <= ef; i++) {	fprintf (fp, "%5d BS: %11d BV: %8d\n", i, vh->bestscore[i], vh->bestvh[i]);		for (j = vh->frame_start[i]; j < vh->frame_start[i+1]; j++) {	    /* This entry */	    b = VITHIST_ID2BLK(j);	    l = VITHIST_ID2BLKOFFSET (j);	    ve = vh->entry[b] + l;	    	    fprintf (fp, "\t%c%6d %5d %5d %11d %9d %8d %7d %4d %s",		     (ve->valid ? ' ' : '*'), j,		     ve->sf, ve->ef, ve->score, ve->ascr, ve->lscr, ve->pred, ve->type,		     dict_wordstr (dict, ve->wid));	    	    fprintf (fp, " (%s", lm_wordstr (lm, ve->lmstate.lm3g.lwid[0]));	    lwid = ve->lmstate.lm3g.lwid[1];	    if (IS_S3LMWID(lwid))		fprintf (fp, ", %s", lm_wordstr (lm, lwid));	    fprintf (fp, ")\n");	}		if (j == vh->frame_start[i])	    fprintf (fp, "\n");    }#if 0        if (vh->lwidlist)	vithist_lmstate_dump (vh, kbc, fp);#endif    fprintf (fp, "END_VITHIST\n");    fflush (fp);}glist_t vithist_backtrace (vithist_t *vh, int32 id){    vithist_entry_t *ve;    int32 b, l;    glist_t hyp;    hyp_t *h;        hyp = NULL;        while (id > 0) {	b = VITHIST_ID2BLK(id);	l = VITHIST_ID2BLKOFFSET(id);	ve = vh->entry[b] + l;		h = (hyp_t *) ckd_calloc (1, sizeof(hyp_t));	h->id = ve->wid;	h->sf = ve->sf;	h->ef = ve->ef;	h->ascr = ve->ascr;	h->lscr = ve->lscr;	h->type = ve->type;	h->vhid = id;		hyp = glist_add_ptr (hyp, h);		id = ve->pred;    }        return hyp;}typedef struct {    s3wid_t wid;    int32 fef, lef;    int32 seqid;	/* Node sequence no. */    glist_t velist;	/* Vithist entries for this dagnode */} dagnode_t;/* * Header written BEFORE this function is called. */void vithist_dag_write (vithist_t *vh, glist_t hyp, dict_t *dict, int32 oldfmt, FILE *fp){    glist_t *sfwid;		/* To maintain <start-frame, word-id> pair dagnodes */    vithist_entry_t *ve, *ve2;    gnode_t *gn, *gn2, *gn3;    dagnode_t *dn, *dn2;    int32 sf, ef, n_node;    int32 f, i;    hyp_t *h;        sfwid = (glist_t *) ckd_calloc (vh->n_frm+1, sizeof(glist_t));        n_node = 0;    for (i = 0; i < vh->n_entry; i++) {	/* This range includes the dummy <s> and </s> entries */	ve = vh->entry[VITHIST_ID2BLK(i)] + VITHIST_ID2BLKOFFSET(i);	if (! ve->valid)	    continue;		/*	 * The initial <s> entry (at 0) is a dummy, with start/end frame = -1.  But the old S3	 * code treats it like a real word, so we have to reintroduce it in the dag file with	 * a start time of 0.  And shift the start time of words starting at frame 0 up by 1.	 * MAJOR HACK!!	 */	if (ve->sf <= 0) {	    assert (ve->sf >= -1);	    assert ((ve->ef == -1) || (ve->ef > 1));	    	    sf = ve->sf + 1;	    ef = (ve->ef < 0) ? 0 : ve->ef;	} else {	    sf = ve->sf;	    ef = ve->ef;	}		for (gn = sfwid[sf]; gn; gn = gnode_next(gn)) {	    dn = (dagnode_t *) gnode_ptr(gn);	    if (dn->wid == ve->wid)		break;	}	if (! gn) {	    dn = (dagnode_t *) ckd_calloc (1, sizeof(dagnode_t));	    dn->wid = ve->wid;	    dn->fef = ef;	    dn->lef = ef;	    dn->seqid = -1;	/* Initially all invalid, selected ones validated below */	    dn->velist = NULL;	    n_node++;	    	    sfwid[sf] = glist_add_ptr (sfwid[sf], (void *) dn);	} else {	    dn->lef = ef;	}		/*	 * Check if an entry already exists under dn->velist (generated by a different	 * LM context; retain only the best scoring one.	 */	for (gn = dn->velist; gn; gn = gnode_next(gn)) {	    ve2 = (vithist_entry_t *) gnode_ptr (gn);	    if (ve2->ef == ve->ef)		break;	}	if (gn) {	    if (ve->score > ve2->score)		gnode_ptr(gn) = (void *)ve;	} else	    dn->velist = glist_add_ptr (dn->velist, (void *) ve);    }        /*     * Validate segments with >1 end times; if only 1 end time, can be pruned.     * But keep segments in the original hypothesis, regardless; mark them first.     */    for (gn = hyp; gn; gn = gnode_next(gn)) {	h = (hyp_t *) gnode_ptr (gn);	for (gn2 = sfwid[h->sf]; gn2; gn2 = gnode_next(gn2)) {	    dn = (dagnode_t *) gnode_ptr (gn2);	    if (h->id == dn->wid)		dn->seqid = 0;	/* Do not discard (prune) this dagnode */	}    }        /* Validate startwid and finishwid nodes */    dn = (dagnode_t *) gnode_ptr(sfwid[0]);    assert (dn->wid == dict_startwid(dict));    dn->seqid = 0;    dn = (dagnode_t *) gnode_ptr(sfwid[vh->n_frm]);    assert (dn->wid == dict_finishwid(dict));    dn->seqid = 0;        /* Now prune dagnodes with only 1 end frame if not validated above */    i = 0;    for (f = vh->n_frm; f >= 0; --f) {	for (gn = sfwid[f]; gn; gn = gnode_next(gn)) {	    dn = (dagnode_t *) gnode_ptr(gn);	    if ((dn->lef > dn->fef) || (dn->seqid >= 0))		dn->seqid = i++;	    else		dn->seqid = -1;		/* Flag: discard */	}    }    n_node = i;        /* Write nodes info; the header should have been written before this function is called */    fprintf (fp, "Nodes %d (NODEID WORD STARTFRAME FIRST-ENDFRAME LAST-ENDFRAME)\n", n_node);    for (f = vh->n_frm; f >= 0; --f) {	for (gn = sfwid[f]; gn; gn = gnode_next(gn)) {	    dn = (dagnode_t *) gnode_ptr(gn);	    if (dn->seqid >= 0) {		fprintf (fp, "%d %s %d %d %d\n",			 dn->seqid, dict_wordstr(dict, dn->wid), f, dn->fef, dn->lef);	    }	}    }    fprintf (fp, "#\n");        fprintf (fp, "Initial %d\nFinal %d\n", n_node-1, 0);    fprintf (fp, "#\n");        fprintf (fp, "BestSegAscr 0 (NODEID ENDFRAME ASCORE)\n");    fprintf (fp, "#\n");        /* Edges */    if (oldfmt)	fprintf (fp, "Edges (FROM-NODEID TO-NODEID ASCORE)\n");    else	fprintf (fp, "Edges (FROM-NODEID ENDFRAME ASCORE)\n");    for (f = vh->n_frm-1; f >= 0; --f) {	for (gn = sfwid[f]; gn; gn = gnode_next(gn)) {	    dn = (dagnode_t *) gnode_ptr(gn);	    /* Look for transitions from this dagnode to later ones, if not discarded */	    if (dn->seqid < 0)		continue;	    	    for (gn2 = dn->velist; gn2; gn2 = gnode_next(gn2)) {		ve = (vithist_entry_t *) gnode_ptr (gn2);				sf = (ve->ef < 0) ? 1 : (ve->ef + 1);				if (oldfmt) {		    for (gn3 = sfwid[sf]; gn3; gn3 = gnode_next(gn3)) {			dn2 = (dagnode_t *) gnode_ptr(gn3);			if (dn2->seqid >= 0)			    fprintf (fp, "%d %d %d\n", dn->seqid, dn2->seqid, ve->ascr);		    }		} else {		    for (gn3 = sfwid[sf]; gn3; gn3 = gnode_next(gn3)) {			dn2 = (dagnode_t *) gnode_ptr(gn3);			if (dn2->seqid >= 0) {			    fprintf (fp, "%d %d %d\n", dn->seqid, sf-1, ve->ascr);			    break;			}		    }		}	    }	}    }    fprintf (fp, "End\n");        /* Free dagnodes structure */    for (f = 0; f <= vh->n_frm; f++) {	for (gn = sfwid[f]; gn; gn = gnode_next(gn)) {	    dn = (dagnode_t *) gnode_ptr(gn);	    	    glist_free (dn->velist);	    ckd_free ((void *) dn);	}		glist_free (sfwid[f]);    }    ckd_free ((void *) sfwid);}/*  * RAH, free memory allocated in vithist_free  */void vithist_free (vithist_t *v){  if (v) {    ckd_free ((void *) v);  }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -