Optimization 距离编码器:如何摆脱分割?
我正在尝试优化视频编解码器,使其在Raspberry Pi上具有良好的性能。一个重要的瓶颈是在范围解码器中进行的32位整数分割,它占用了18%的解码时间。由于该设备的ARM处理器显然缺少整数除法指令,我认为可以很容易地对此进行优化。划分必须准确 该除法中的除数和除数在每次调用中都是不同的,但众所周知,除数总是小于65536。我想建立一个逆除数值的查找表。用那张表我可以用乘法代替除法。查找表的大小将为256 KB 问题Optimization 距离编码器:如何摆脱分割?,optimization,arm,integer-division,raspberry-pi,range-encoding,Optimization,Arm,Integer Division,Raspberry Pi,Range Encoding,我正在尝试优化视频编解码器,使其在Raspberry Pi上具有良好的性能。一个重要的瓶颈是在范围解码器中进行的32位整数分割,它占用了18%的解码时间。由于该设备的ARM处理器显然缺少整数除法指令,我认为可以很容易地对此进行优化。划分必须准确 该除法中的除数和除数在每次调用中都是不同的,但众所周知,除数总是小于65536。我想建立一个逆除数值的查找表。用那张表我可以用乘法代替除法。查找表的大小将为256 KB 问题 执行该优化是一个好主意吗 有没有更好的办法摆脱软件部门 有没有一种不同的方法来
如果你想使用魔法乘法+LUT,这里有一些代码 测试随机因子的简单测试仪。没有彻底测试我所有的,但在我运行它的短时间内工作过。似乎对i的i测试的所有32位被除数状态(j=0..2^32-1)都有效 实际上,您可能会为i=2..64k-1或类似的某个范围预计算一个查找表(i=0不起作用,因为值/0未定义;i=1不起作用,因为该值的魔法乘法器刚好在32位数字的范围之外)。然后使用使用i作为查找索引的等式来获得魔法乘数'm'。根据需要改变&不要讨厌我的风格:P
#include <stdio.h>
int main() {
unsigned int i,j,k,m,c;
// compute j/i,
// compute k = 2^32/i
// instead of j/i, use m = ~(j*k)>>32
srand(time(0));
for(c=0;c<64;c++) {
// generate random divisor i's for testing, then fully test every j
i = rand()&0x7fff;
// precompute these and put into a lookup table, index on [i]
k = (((__int64)1)<<32)/i;
for(j=0;j!=-1;j++) {
// status updater so we know it's working...
if(!(j&0xfffff)) { printf("%d : %d \r", i, j); fflush(0); }
// multiply instead of divide!
m = (((__int64)j*k)+k/2)>>32;
// rare fixup
if(j - m*i >= i) m++;
if(m != j/i) {
// as long as this line doesn't print, we're ok
printf("wrong : %d %d %d got: %d should be: %d\n",
i, j, k, m, j/i);
}
}
}
}
#包括
int main(){
无符号整数i,j,k,m,c;
//计算j/i,
//计算k=2^32/i
//使用m=~(j*k)>>32代替j/i
srand(时间(0));
对于(c=0;c>32;
//难得一见
如果(j-m*i>=i)m++;
如果(m!=j/i){
//只要这行不打印,我们就没事
printf(“错误:%d%d%d得到的:%d应该是:%d\n”,
i、 j,k,m,j/i);
}
}
}
}
人们还可以利用这样一个事实,Raspberry Pi包括一个能够执行双精度FP除法的FP单元,这比整数除法的软件模拟要快。将所有整数除法a=b/c
替换为a=(double)b/(double)c
对我来说是可行的