一、预备知识:音频信号压缩的依据——人类听觉系统的感知特性
心理声学模型 (Psychoacoustic model)
生理 (Physiological)感知极限(传感极限)
心理 (Psychological) 感知极限 (信号处理极限)
1.听觉系统中存在一个听觉阈值电平,低于这个电平的声音信号就听不到。
- 听觉阈值的大小随声音频率的改变而改变。
- 一个人是否听到声音取决于声音的频率,以及声音的幅度是否高于这种频率下的听觉阈值。
2.听觉掩蔽特性。即听觉阈值电平是自适应的,会随听到的
不同频率声音而发生变化。一个强纯音会掩蔽在其附近同时发声的弱纯音。
3.临界频带是指当某个纯音被以它为中心频率、且具有一定带宽的连续噪声所掩蔽时,如果该纯音刚好被听到时的功率等于这一频带内的噪声功率,这个带宽为临界频带宽度。掩蔽效应在一定频率范围内不随带宽增大而改变,直至超过某个频率值。
4.人类听觉系统大致等效于一个信号通过一组并联的不同中心频率的带通滤波器。
二、MPEG-1 Audio LayerII 编码器原理
1.多相滤波器(用于分隔子带)
layer 1分成32个相等的子带
2.量化和编码
对各个子带每
12 个样点进行一次比例因子计算。先定出 12 个样点中绝对值的最大值。查比例因子表中比这个最大值大的最小值作为比例因子。用 6 比特表示。
第 2 层的一帧对应 36 个子带样值,是第 1 层的三倍,原则上要传三个比例因子。为了降低比例因子的传输码率,采用了利用人耳时域掩蔽特性的编码策略。
每帧中每个子带的三个比例因子被一起考虑,划分成特定的几种模式。根据这些模式, 1 个、 2 个或 3 个比例因子和比例因子选择信息(每子带 2 比特)一起被传送。如
果一个比例因子和下一个只有很小的差别,就只传送大的一个,这种情况对于稳态信号经常出现。
使用这一算法后,和第 1 层相比,第 2 层传输的比例因子平均减少了 2 个,即传输率由 22.5Kb/s 降低到了7.5Kb/s 。
对每个子带计算掩蔽 噪声 比 MNR ,信噪比 SNR 信掩比 SMR
即 MNR = SNR-SMR
三、代码调试。
1.main函数的主要功能
/************************************************************************
*
* main
*
* PURPOSE: MPEG II Encoder with
* psychoacoustic models 1 (MUSICAM) and 2 (AT&T)
*
* SEMANTICS: One overlapping frame of audio of up to 2 channels are
* processed at a time in the following order:
* (associated routines are in parentheses)
*
* 1. Filter sliding window of data to get 32 subband
* samples per channel.每32个子带样本每个子带滤波器产生一个样本输出
* (window_subband,filter_subband)
*
* 2. If joint stereo mode, combine left and right channels
* for subbands above #jsbound#.对有立体声的情况加入左右声道
* (combine_LR)
*
* 3. Calculate scalefactors for the frame, and
* also calculate scalefactor select information.计算框架的比例因子,以及比例因子选择信息
* (*_scale_factor_calc)
*
* 4. Calculate psychoacoustic masking levels using selected
* psychoacoustic model.使用选定的模型计算心理声学掩蔽程度。
* (psycho_i, psycho_ii)
*
* 5. Perform iterative bit allocation for subbands with low
* mask_to_noise ratios using masking levels from step 4.对低频段的子带执行迭代位分配。使用第4步的掩蔽电平。
* (*_main_bit_allocation)
*
* 6. If error protection flag is active, add redundancy for
* error protection..如果错误保护标志有效,则添加纠错。
* (*_CRC_calc)
*
* 7. Pack bit allocation, scalefactors, and scalefactor select
*headerrmation onto bitstream.打包bit分配、比例因子和比例因子选择到比特流。
* (*_encode_bit_alloc,*_encode_scale,transmission_pattern)
*
* 8. Quantize subbands and pack them into bitstream量化子带并将其打包到比特流中
* (*_subband_quantization, *_sample_encoding)
*
************************************************************************/
2.main函数代码分析
解析命令行
programName = argv[0];
if (argc == 1) /* no command-line args */
short_usage ();
else
parse_args (argc, argv, &frame, &model, &num_samples, original_file_name,
encoded_file_name);
print_config (&frame, &model, original_file_name, encoded_file_name);
/* this will load the alloc tables and do some other stuff */
hdr_to_frps (&frame);
nch = frame.nch;
error_protection = header.error_protection;
读取帧信息
while (get_audio(musicin, buffer, num_samples, nch, &header) > 0) {
if (glopts.verbosity > 1)
if (++frameNum % 10 == 0)
fprintf(stderr, "[%4u]\r", frameNum);
fflush(stderr);
win_buf[0] = &buffer[0][0];
win_buf[1] = &buffer[1][0];
adb = available_bits(&header, &glopts);
lg_frame = adb / 8;
if (header.dab_extension) {
/* in 24 kHz we always have 4 bytes */
if (header.sampling_frequency == 1)
header.dab_extension = 4;
/* You must have one frame in memory if you are in DAB mode */
/* in conformity of the norme ETS 300 401 http://www.etsi.org */
/* see bitstream.c */
if (frameNum == 1)
minimum = lg_frame + MINIMUM;
adb -= header.dab_extension * 8 + header.dab_length * 8 + 16;
}
{
int gr, bl, ch;
/* New polyphase filter
Combines windowing and filtering. Ricardo Feb'03 */
for (gr = 0; gr < 3;