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

📄 fe_feature.cpp

📁 这是一个语音特征提取的程序源码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
			break;
		case FE_PARCOR:
			_lpc_parcor_basic(&frameA[0], frameSize, &acf[0], &featA[n][0], m_lpcOrder, &G);
			featA[n][0] = 0;
			break;
		case FE_FORMANT:
			{
				vector<CComplex> rootsA(m_lpcOrder+1);
				for(i=0;i<=m_lpcOrder;i++) rootsA[i] = 0;
				_lpc_basic(&frameA[0], frameSize, &acf[0], m_lpcOrder, &G);
				/* Note that we compute all formant frequencies for post-processing */
				int ntmp=lpc_to_formant(&acf[0],m_lpcOrder,&featTmpA[n][0],m_lpcOrder/2,rootsA);
				for(k=0;k<=m_lpcOrder/2;k++) featTmpA[n][k] *= (m_sampleRate/(float)(2*M_PI));
			}
			break;
		case FE_LPC:
			_lpc_basic(&frameA[0], frameSize, &featA[n][0], m_lpcOrder, &G);
			break;
		case FE_FBANK:
			_filterbank_basic(&frameA[0], frameSize, &featA[n][0], m_fbOrder, fft_size, m_cepSmooth, (int)(m_sampleRate/MAX_PITCH_FREQ));
			break;
		case FE_MFCC:
			_mel_cepstrum_basic(&frameA[0], frameSize, &featA[n][0], m_fbOrder, m_cepOrder, m_fftSize);
			cepstral_window(&featA[n][0],m_cepOrder,m_lifter);
			break;
		case FE_PLCC:
			_plp_basic(&frameA[0], frameSize, &featA[n][0], m_plccOrder, m_plpOrder);
			cepstral_window(&featA[n][0],m_plccOrder,m_lifter);
			break;
		case FE_LPCC:
			_lpc_basic(&frameA[0], frameSize, &acf[0], m_lpcOrder, &G);
			lpc_to_cepstrum(&acf[0], m_lpcOrder, &featA[n][0], m_cepOrder, G);
			cepstral_window(&featA[n][0],m_cepOrder,m_lifter);
			break;
		case FE_FTCC:
			_fft_cepstrum_basic(&frameA[0], frameSize, &featA[n][0], m_cepOrder, fft_size);
			cepstral_window(&featA[n][0],m_cepOrder,m_lifter);
			break;
		default:
			assert(0);
			return 0;
			break;
		}
	}

	if(fk==FE_FORMANT){
		/* check formant range, noting that F0 is always zero */
		formant_check_range(featTmpA, m_lpcOrder/2, frameN);

		/* smooth formant trajectory */
		formant_median_filter(featTmpA, m_lpcOrder/2, frameN);
		formant_linear_filter(featTmpA, m_lpcOrder/2, frameN);

		/* Make formant consistent with pitch information */
		assert(m_pitchA.size()>0);
		frameN = formant_remove_nonvoice(featTmpA, m_lpcOrder/2, frameN, m_pitchA);

		/* Copy to the result variable, skipping F0  */
		for(n=0;n<frameN;n++){
			for(int k=0;k<dimN && k<m_lpcOrder/2+1;k++){
				featA[n][k]=featTmpA[n][k+1];
			}
		}

	}
	return frameN;
}


int Fe::ReadParaFile(const char *parafile)
{
	FILE *fi = fopen(parafile,"r");
	if(!fi) return 0;
	char line[1024], arg1[256], arg2[256];
	string name;
	while(fgets(line,sizeof(line)-1,fi)){
		if(line[0]==0) break; // end of file
		if(line[0]=='#') continue; // skip comment line
		sscanf(line,"%s%s", arg1, arg2);
		name=arg1;
		if(name=="SAMPLING_RATE"){ m_sampleRate = atoi(arg2); } 
		else if(name=="WINDOW_SIZE"){ m_winSizeMs = atoi(arg2); } 
		else if(name=="SHIFT_SIZE"){ m_shiftSizeMs = atoi(arg2); } 
		else if(name=="PREEMPHASIS_FACTOR"){ m_emphFac = (float)atof(arg2); } 
		else if(name=="FFT_SIZE"){ m_fftSize = atoi(arg2); } 
		else if(name=="LPC_ORDER"){ m_lpcOrder = atoi(arg2); } 
		else if(name=="CEPSTRUM_ORDER"){ m_cepOrder = atoi(arg2); } 
		else if(name=="PLP_ORDER"){ m_plpOrder = atoi(arg2); } 
		else if(name=="PLP_CEPSTRUM_ORDER"){ m_plccOrder = atoi(arg2); } 
		else if(name=="FILTER_BANK_ORDER"){ m_fbOrder = atoi(arg2); } 
		else if(name=="CEPSTRAL_SMOOTHING"){ m_cepSmooth = (strcmp(arg2,"ON")==0); } 
		else if(name=="DITHERING"){ m_dither = (strcmp(arg2,"ON")==0); } 
		else if(name=="TEMPORAL_FILTER_SIZE"){ m_deltaSize = atoi(arg2); }
	}
	fclose(fi);
	return 1;
}


int Fe::ReadTag(const char *tag, int* pTag, int ndim)
{
	int i;
	for(i=0;i<ndim;i++) pTag[i] = 0;
	if(!tag){
		for(i=0;i<ndim;i++) pTag[i] = 1;
		return 1;
	}
	
	vector<char> tmp(strlen(tag)+1);
	strcpy(&tmp[0],tag);
	char* tmp_save = NULL;
	char* p = strtok_r(&tmp[0], " ,", &tmp_save);
	if(!p){
		for(i=0;i<ndim;i++) pTag[i] = 1;
	}

	while(p){
		int begin = 0, end = 0;
		int len = strlen(p);
		char* p_save = NULL;
		if(*p == '-'){
			begin = 0;
			if(*(p+1) != '\0')
				end = atoi(p+1);
			else
				end = -1;
		}
		else if(*(p+len-1) == '-'){
			end = ndim-1;
			*(p+len-1) = '\0';
			begin = atoi(p);
		}
		else{
			char* q = strtok_r(p, "-", &p_save);
			if(q) begin = end = atoi(q);
			q = strtok_r(NULL, "-", &p_save);
			if(q) end = atoi(q);
		}
		for(i=begin; i<=end; i++) pTag[i] = 1;
		p = strtok_r(NULL, " ,", &tmp_save);
	}
	return 1;
}


int Fe::GetShiftSize()
{
	int nshift = (int)((m_shiftSizeMs*m_sampleRate)/1000.0+0.5);
	if(nshift%2) nshift += 1;
	return nshift;
}


int Fe::GetFrameSize()
{
	int frameSize = (int)((m_winSizeMs*m_sampleRate)/1000.0+0.5);
	if(frameSize%2) frameSize += 1;
	return frameSize;
}


const char *GetFeatName(FeatKind fk)
{
	assert((int)fk>=0 && (int)fk<(int)FE_NUM_FEAT);
	return FE_featNameA[(int)fk];
}


string GetFeatExtension(FeatKind fk)
{
	FeatKind bk=GetBaseFeatKind(fk);
	string name=GetFeatName(bk);
	for(int i=0;i<name.size();i++) name[i]=tolower(name[i]);
	if(HasDeltaFeat(fk)) name=name+"_d";
	if(HasStftFeat(fk)) {
		int k=name.find("_stft");
		name=name.substr(0,k);
		name=name+"_s";
	}
	return name;
}


FeatKind GetBaseFeatKind(FeatKind fk)
{
	string name=GetFeatName(fk);
	int k=name.find("_D");
	if(k==string::npos) return fk;
	if(name[k+2]==0 || name[k+2]=='_'){
		name=name.substr(0,k);
		for(int i=0;i<FE_NUM_FEAT-1;i++){
			if(strcmp(FE_featNameA[i],name.c_str())==0) return (FeatKind)i;
		}
	}
	return fk;
}


FeatKind FeatName2Kind(const char* name)
{
	int i;
	for(i=0;i<FE_NUM_FEAT-1;i++){
		if(strcmp(FE_featNameA[i],name)==0) return (FeatKind)i;
	}
	return (FeatKind)i;
}


int HasDeltaFeat(FeatKind fk)
{
	const char *name=GetFeatName(fk);
	char *i=strstr(name,"_D");
	if(i) return 1;
	else return 0;
}


int HasStftFeat(FeatKind fk)
{
	const char *name=GetFeatName(fk);
	char *i=strstr(name,"_SPEC");
	if(i) return 1;
	else return 0;
}


int Fe::GetDim(FeatKind fk)
{
	int ndim = 0;
	fk=GetBaseFeatKind(fk);
	switch(fk){
		case FE_LPC: case FE_LPCCOV:
			ndim = m_lpcOrder + 1; break;
		case FE_LPCC: case FE_MFCC: case FE_FTCC:
			ndim = m_cepOrder + 1; break;
		case FE_PLCC:
			ndim = m_plccOrder + 1; break;	
		case FE_FBANK:
			ndim = m_fbOrder; break;
		case FE_LAR: case FE_LSF: case FE_PARCOR:
			ndim = m_lpcOrder + 1; break;
		case FE_FORMANT:
			/* F1, F2, F3, F4 */
			ndim = 4; break;
		case FE_FFT_SPEC: case FE_LPC_SPEC: case FE_LPCC_SPEC:
		case FE_MFCC_SPEC: case FE_FTCC_SPEC:
			ndim = m_fftSize; break;
		case FE_FFTCEP:
			ndim = m_fftSize; break;
		case FE_ZCR: case FE_ENERGY: case FE_PITCH: case FE_VUS: case FE_ENDPOINT:
		case FE_EPOCH: case FE_GLOFLOW: case FE_GLOPULSE: case FE_LPCRES:
			ndim = 1; break;
		default:
			ndim = 1; break;
	}
	return ndim;
}


int GetDefaultDim(enum FeatKind fk)
{
	int dim=0;
	fk=GetBaseFeatKind(fk);
	switch(fk){
	case FE_FFT_SPEC: case FE_LPC_SPEC: case FE_LPCC_SPEC: case FE_MFCC_SPEC: case FE_FTCC_SPEC:
		dim = DEFAULT_FFT_SIZE/2+1; break;
	case FE_FFTCEP:
		dim = DEFAULT_FFT_SIZE/2+1; break;
	case FE_LPC: case FE_LPCCOV: case FE_LAR: case FE_LSF: case FE_PARCOR:
		dim = FE_LPC_ORDER+1; break;
	case FE_FBANK:
		dim = FE_NUM_CHANNELS+1; break;
	case FE_LPCC: case FE_FTCC: case FE_MFCC:
		dim = FE_CEP_ORDER+1; break;
	case FE_PLCC:
		dim = PLP_CEP_ORDER+1; break;
	case FE_FORMANT:
		dim = 4; break;
	default:
		dim = 1; break;
	}
	return dim;
}


int GetDefaultOrder(enum FeatKind fk)
{
	int order=1;
	fk=GetBaseFeatKind(fk);
	switch(fk){
	case FE_FFT_SPEC:
		order = DEFAULT_FFT_SIZE/2+1; break;
	case FE_FFTCEP:
		order = DEFAULT_FFT_SIZE/2+1; break;
	case FE_LPC_SPEC:
		order = FE_LPC_ORDER; break;
	case FE_LPCC_SPEC: case FE_MFCC_SPEC: case FE_FTCC_SPEC:
		order = FE_CEP_ORDER; break;
	case FE_LPC: case FE_LPCCOV: case FE_LAR: case FE_LSF: case FE_PARCOR:
		order = FE_LPC_ORDER; break;
	case FE_FBANK:
		order = FE_NUM_CHANNELS; break;
	case FE_LPCC: case FE_FTCC: case FE_MFCC: case FE_PLCC:
		order = PLP_CEP_ORDER; break;
	case FE_FORMANT:
		order = 4; break;
	default:
		order = 1; break;
	}
	return order;
}


float Fe::LogE(float x)
{
	if(x>m_energyFloor) return log(x);
	else return m_logEnergyFloor;
}


int Fe::Integrate(float *a, int n, short *b)
{
	float alpha = (float)0.98;
	static float prev = 0;
	for(int i=0;i<n;i++){	
		prev = a[i] + alpha*prev;
		b[i] = (short)(prev);
	}
	return 1;
}


int Fe::Integrate(short *a, int n, short *b)
{
	float alpha = (float)0.98;
	static float prev = 0;
	for(int i=0;i<n;i++){	
		prev = a[i] + alpha*prev;
		b[i] = (short)(prev);
	}
	return 1;
}


float Fe::GetMedian(float* a, int n)
{
	int i;
	float median = 0;
	vector<float> tmp(n);;
	for(i=0;i<n;i++)
		tmp[i] = a[i];

	qsort(&tmp[0],n,sizeof(float),FE_CompareFloat);
	median = tmp[(n-1)/2];
	return median;
}


int Fe::InitProgress(int* pProgress, int* pCancel)
{	
	m_pProgress = pProgress;
	m_pCancel = pCancel;
	return 1;
}


int Fe::CheckWinMessage()
{
#if defined(_WIN32) && defined(ANALYSIS_LIB)
	MSG message;
	if(PeekMessage(&message, NULL, 0, 0, PM_REMOVE)) {
		TranslateMessage(&message);
		DispatchMessage(&message);
	}
#endif
	if(m_pCancel && (*m_pCancel)) return 0;
	else return 1;
}


int Fe::ShowProgress(int progress)
{
#if defined(_WIN32) && defined(ANALYSIS_LIB)
	if(m_pProgress) *m_pProgress = progress;
#endif
	return 1;
}


int FE_CompareFloat(const void *a, const void *b)
{
	float *aa = (float*)a;
	float *bb = (float*)b;
	if(*aa > *bb) return 1;
	else if(*aa < *bb) return -1;
	else return 0;
}


#ifdef WIN32
char* strtok_r(char *s1, const char *s2, char **savept)
{
	char *p = NULL;
	char *z = NULL;
	
	if(s1) *savept = s1;
	if((*savept) == NULL) return NULL;
	z = *savept + strlen(*savept);
	p = strtok(*savept,s2);
	if(p != NULL && (p + strlen(p) + 1) < z)
		*savept = p + strlen(p) + 1;
	else
		*savept = NULL;
	return p;
}
#endif

⌨️ 快捷键说明

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