标题有点难想 , 见谅 , 小细节的问题也有点多 , 请海函。
首先我写了份 bitwise - bitcount 函式 , 做成 template
最初版是写成这样
template<typename T> inline
size_t bitcount(T v) // slow but generation
{
size_t c ;
for(c = 0 ; v &= v - 1; ++c) ;
return c;
}
鉴于效能 , 接着对每种 pod type 做特偏化
template<> inline size_t bitcount(unsigned char v) {}
template<> inline size_t bitcount(unsigned short v) {}
template<> inline size_t bitcount(unsigned int v) {}
template<> inline size_t bitcount(unsigned long v) {}
template<> inline size_t bitcount(unsigned long long v) {}
接着我再回到最原始版的 template , 打算根据 bytes 数去呼叫不同版本的 bitcount
同时想考虑可能有超过 8 bytes 的情况 , 像是 non-padding struct 或 array
可能会用到
template<typename T> inline
size_t bitcount(T v)
{
size_t icount = 0;
switch( size_t ibytes = sizeof(T) )
{
case 8 : return bitcount<unsigned char > (v) ;
case 4 : return bitcount<unsigned int > (v) ;
case 2 : return bitcount<unsigned short> (v) ;
case 1 : return bitcount<unsigned long long> (v) ;
default :
// 一次处理 4 bytes
unsigned int * puint = (unsigned *) & v;
for(size_t itimes = 0 ; itimes < ibytes / 4 ; ++itimes)
icount+=bitcount<unsigned int>( * puint ++);
// 剩下没处理完的逐一 byte 处理
unsigned char * pchar = (unsigned char *) puint ;
for(size_t itimes = 0; itimes < ibytes % 4 ; ++itimes)
icount+=bitcount<unsigned char>( *pchar++);
}
return icount ;
}
东西是做出来了没错,但截至目前为止有几个问题想请教。
1. 资料型态问题
先拿另一份 code 来讲
template<typename T>
T mask_low_nbits(T v , int n)
{
T msk = (1 << n) - 1 ; // 这个有问题
return v & msk ;
}
(1.1) 上面这段在 unsigned long long 时会出包,一般这情况会怎写?
T v = (1ULL << n) - 1 ;
T v = (static_cast<T>(1) << n) - 1 ;
或是有比较建议的方法吗?
(1.2) 上面的 T , 请问有没有办法判断传进来的是 unsigned type ?
目前我找不到相关资料说明 (虽然我觉得不太可能办到)
2. 自动展开
最终的 template<typename T> size_t bitcount(T v) ; 在非特定 bytes
数下,我是用 for loop 展开,想请问有没有类似以下的想法让 template
帮我自己展开 ? ( compile error .. )
template<typename T , size_t nbytes = sizeof(T)>
size_t bitcount(T v)
{
if(nbytes > 4) {
return
bitcount<unsigned> ( v )
+ bitcount<unsigned , nbytes-4 > ( *((unsigned*)& v + 1 ) ) ;
}
else if(nbytes) {
return
bitcount<unsigned char> ( v )
+ bitcount<unsigned char , nbytes-1> ( *( (unsigned char*) &v +1));
}
}
3. Resource
(3.1) 另想知道有没有文章或是书可以教一些这方面的技巧?
(3.2) 我用 VS 写 template 的时候,发现 keyin source code ,
IDE 在做 template tips 时, " 好像 " 会比较 lag ,
请问是我的心理因素 , 还是也有人会这样 ?