1 /*-------------- Telecommunications & Signal Processing Lab ---------------
2 McGill University
3
4 Routine:
5 struct MOVB_NMR PQmovNMRB (const double EbN[], const double Ehs[],
6 const struct Par_NMR *NMR)
7 void PQavgNMRB (const struct MOVC_NMR *NMR, int Nchan, int Np,
8 double *TotalNMRB, double *RelDistFramesB)
9
10 Purpose:
11 Calculate the noise-to-mask ratio (PEAQ Basic version)
12 Calculate the NMR model output variables (PEAQ Basic version)
13
14 Description:
15 PQmovNMRB:
16 This routine calculates the average and maximum noise-to-mask ratio for a
17 frame of data (PEAQ Basic Version).
18
19 PQavgNMRB:
20 This routine averages the NMR values to give the NMR model output variables.
21
22 Parameters:
23 PQmovNMRB:
24 <- struct MOVB_NMR
25 Output structure with NMR values
26 -> const double EbN[]
27 Noise patterns
28 -> const double Ehs[]
29 Excitation patterns
30 -> const struct Par_NMR *NMR
31 Structure with NMR tables
32
33 PQavgNMRB:
34 -> const struct MOVC_NMR *NMR
35 Structure containing the NMR values for each PEAQ frame
36 -> int Nchan
37 Number of channels
38 -> int Np
39 Number of PEAQ frames
40 <- double *TotalNMRB
41 Model Output variable
42 <- double *RelDistFramesB
43 Model Output variable
44
45 Author / revision:
46 P. Kabal Copyright (C) 2003
47 $Revision: 1.7 $ $Date: 2003/05/13 01:15:13 $
48
49 -------------------------------------------------------------------------*/
50
51 #include <math.h>
52
53 #include "PQevalAudio.h"
54
55 #define DBP(x) (10.0 * log10 (x))
56
57 static double
58 PQ_FractThr (double Thr, const double x[], int N);
59 static double
60 PQ_LinAvg (const double x[], int N);
61
62
63 struct MOVB_NMR
PQmovNMRB(const double EbN[],const double Ehs[],const struct Par_NMR * NMR)64 PQmovNMRB (const double EbN[], const double Ehs[], const struct Par_NMR *NMR)
65
66 {
67 int m;
68 double s, NMRm;
69 struct MOVB_NMR NMRV;
70
71 const int Nc = NMR->Nc;
72 const double *gm = NMR->gm;
73
74 NMRV.NMRmax = 0;
75 s = 0;
76 for (m = 0; m < Nc; ++m) {
77 NMRm = EbN[m] / (gm[m] * Ehs[m]);
78 s += NMRm;
79 if (NMRm > NMRV.NMRmax)
80 NMRV.NMRmax = NMRm;
81 }
82 NMRV.NMRavg = s / Nc;
83
84 return NMRV;
85 }
86
87 /* Average NMR values */
88
89 void
PQavgNMRB(const struct MOVC_NMR * NMR,int Nchan,int Np,double * TotalNMRB,double * RelDistFramesB)90 PQavgNMRB (const struct MOVC_NMR *NMR, int Nchan, int Np, double *TotalNMRB,
91 double *RelDistFramesB)
92
93 {
94 int j;
95 double s, Thr;
96
97 const double ThrdB = 1.5; /* Threshold in dB */
98 Thr = pow (10, ThrdB / 10);
99
100 /* Average log values */
101 s = 0;
102 for (j = 0; j < Nchan; ++j)
103 s += DBP (PQ_LinAvg (NMR->NMRavg[j], Np));
104 *TotalNMRB = s / Nchan;
105
106 s = 0;
107 for (j = 0; j < Nchan; ++j)
108 s += PQ_FractThr (Thr, NMR->NMRmax[j], Np);
109 *RelDistFramesB = s / Nchan;
110
111 return;
112 }
113
114 /* Fraction of values above a threshold */
115
116 static double
PQ_FractThr(double Thr,const double x[],int N)117 PQ_FractThr (double Thr, const double x[], int N)
118
119 {
120 int Nv, i;
121 double Fd;
122
123 Nv = 0;
124 for (i = 0; i < N; ++i) {
125 if (x[i] > Thr)
126 ++Nv;
127 }
128
129 if (N > 0)
130 Fd = ((double) Nv) / N;
131 else
132 Fd = 0;
133
134 return Fd;
135 }
136
137 /* Linear average */
138
139 static double
PQ_LinAvg(const double x[],int N)140 PQ_LinAvg (const double x[], int N)
141
142 {
143 int i;
144 double s;
145
146 s = 0;
147 for (i = 0; i < N; ++i)
148 s += x[i];
149
150 if (N > 0)
151 s = s / N;
152
153 return s;
154 }
155