浏览 4571 次
精华帖 (3) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
|
|
---|---|
作者 | 正文 |
发表时间:2010-08-20
最后修改:2010-10-07
解码一帧Layer3第2步:解码增益因子 -- getScaleFactors_1()和getScaleFactors_2()方法
增益因子(Scale Factor)数据存储在帧内的主信息中。主信息包含增益因子和用哈夫曼编码的主数据(main_data)。增益因子简单讲就是逆量化公式的指数中的一个因子。手册中解码主数据的伪码算法如下,其中MPEG 1.0由ISO/IEC 11172-3给出,MPEG 2.0由ISO/IEC 13818-3给出。官方并没有MPEG2.5这个版本,这个版本是民间版本。
解码MPEG 1.0的增益因子时用到的输入值:
解码MPEG 2.0的增益因子时用到的输入值:
解码增益因子得到的值:
解码MPEG 1.0和MPEG 2.0/2.5增益因子的方法差别很大,这里定义了两个版本的方法。这里涉及到的“纯短块”、“长块”、“混合块”、“窗”概念,在逆量化中再作说明。根据上面对常量及变量值的描述中提及的“共用”、“块的类型”、“窗”就很容易看懂getScaleFactors_x()方法中的if语句和for语句的作用;短块内每个子带分3窗,所以有2重循环。
class Layer3内定义的getScaleFactors_x()方法源码: //2. //>>>>SCALE FACTORS======================================================== private static int[][] scfL; // [2][23]; private static int[][][] scfS; // [2][3][13]; private static int[] i_slen2; // MPEG 2.0 slen for intensity stereo private static int[] n_slen2; // MPEG 2.0 slen for 'normal' mode // slen: 增益因子(scalefactor)比特数 private static byte[][][] nr_of_sfb;//[3][6][4] /* * MPEG 2.0/2.5 */ private void getScaleFactors_2(final int ch, final int gr) { byte[] nr; int i, bandIdx, win, slen, num, n = 0, scf = 0; boolean i_stereo = objHeader.isIStereo(); GRInfo gri = objSI.ch[ch].gr[gr]; int[] l = scfL[ch]; int[][] s = scfS[ch]; rzero_bandL = 0; if ((ch > 0) && i_stereo) slen = i_slen2[gri.scalefac_compress >> 1]; else slen = n_slen2[gri.scalefac_compress]; gri.preflag = (slen >> 15) & 0x1; gri.part2_bits = 0; if (gri.block_type == 2) { n++; if ((gri.mixed_block_flag) != 0) n++; nr = nr_of_sfb[n][(slen >> 12) & 0x7]; for (i = 0; i < 4; i++) { num = slen & 0x7; slen >>= 3; if (num != 0) { for (bandIdx = 0; bandIdx < nr[i]; bandIdx += 3) { for (win = 0; win < 3; win++) s[win][scf] = bsMainInfo.getBits17(num); scf++; } gri.part2_bits += nr[i] * num; } else { for (bandIdx = 0; bandIdx < nr[i]; bandIdx += 3) { for (win = 0; win < 3; win++) s[win][scf] = 0; scf++; } } } n = (n << 1) + 1; for (i = 0; i < n; i += 3) { for (win = 0; win < 3; win++) s[win][scf] = 0; scf++; } } else { nr = nr_of_sfb[n][(slen >> 12) & 0x7]; for (i = 0; i < 4; i++) { num = slen & 0x7; slen >>= 3; if (num != 0) { for (bandIdx = 0; bandIdx < nr[i]; bandIdx++) l[scf++] = bsMainInfo.getBits17(num); gri.part2_bits += nr[i] * num; } else { for (bandIdx = 0; bandIdx < nr[i]; bandIdx++) l[scf++] = 0; } } n = (n << 1) + 1; for (i = 0; i < n; i++) l[scf++] = 0; } } /* * MPEG 1.0 */ private static final int slen0[] = { 0, 0, 0, 0, 3, 1, 1, 1, 2, 2, 2, 3, 3, 3, 4, 4 }; private static final int slen1[] = { 0, 1, 2, 3, 0, 1, 2, 3, 1, 2, 3, 1, 2, 3, 2, 3 }; private void getScaleFactors_1(final int ch, final int gr) { GRInfo gri = objSI.ch[ch].gr[gr]; int scale_comp = gri.scalefac_compress; int length0 = slen0[scale_comp]; int length1 = slen1[scale_comp]; int sfb, win; int[] l = scfL[ch]; int[][] s = scfS[ch]; gri.part2_bits = 0; if (gri.window_switching_flag != 0 && gri.block_type == 2) { if (gri.mixed_block_flag != 0) { // MIXED block gri.part2_bits = 17 * length0 + 18 * length1; for (sfb = 0; sfb < 8; sfb++) l[sfb] = bsMainInfo.getBits9(length0); for (sfb = 3; sfb < 6; sfb++) for (win = 0; win < 3; win++) s[win][sfb] = bsMainInfo.getBits9(length0); for (sfb = 6; sfb < 12; sfb++) for (win = 0; win < 3; win++) s[win][sfb] = bsMainInfo.getBits9(length1); } else { // pure SHORT block gri.part2_bits = 18 * (length0 + length1); for (sfb = 0; sfb < 6; sfb++) for (win = 0; win < 3; win++) s[win][sfb] = bsMainInfo.getBits9(length0); for (sfb = 6; sfb < 12; sfb++) for (win = 0; win < 3; win++) s[win][sfb] = bsMainInfo.getBits9(length1); } } else { // LONG types 0,1,3 int[] scfsi = objSI.ch[ch].scfsi; if (gr == 0) { gri.part2_bits = 10 * (length0 + length1) + length0; for (sfb = 0; sfb < 11; sfb++) l[sfb] = bsMainInfo.getBits9(length0); for (sfb = 11; sfb < 21; sfb++) l[sfb] = bsMainInfo.getBits9(length1); } else { gri.part2_bits = 0; if (scfsi[0] == 0) { for (sfb = 0; sfb < 6; sfb++) l[sfb] = bsMainInfo.getBits9(length0); gri.part2_bits += 6 * length0; } if (scfsi[1] == 0) { for (sfb = 6; sfb < 11; sfb++) l[sfb] = bsMainInfo.getBits9(length0); gri.part2_bits += 5 * length0; } if (scfsi[2] == 0) { for (sfb = 11; sfb < 16; sfb++) l[sfb] = bsMainInfo.getBits9(length1); gri.part2_bits += 5 * length1; } if (scfsi[3] == 0) { for (sfb = 16; sfb < 21; sfb++) l[sfb] = bsMainInfo.getBits9(length1); gri.part2_bits += 5 * length1; } } } } //<<<<SCALE FACTORS========================================================
【本程序下载地址】http://jmp123.sourceforge.net/ 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |