您的位置:首页 > 其它

使用模板元在编译期间进行字节顺序的判断并且转换为相应字节顺序(大小端法转换)(原)

2012-12-15 00:09 260 查看
              使用模板元在编译期间进行字节顺序的判断并且转换为相应字节顺序(大小端法转换)(原)

  首先,开篇我先简单提提什么是模板元编程.模板元编程就是使用模板,在编译期间计算出一定的结果.例如我们在代码里面写有

  

int fun(int x,int y){
return x + y;
}

assert(fun(100, 20) == 120);


可能大家都会写过这样的函数,在这个时候你会觉得与其fun(100,20)这样调用,不如直接写120,那肯定会让程序快点
但是,问题可能不会那么简单,例如你想在代码里面表达654M这个大小,但是你又不想写 685768704 这样一个奇怪的数字进去你的代码.
问题可能会比现在你所看到的或者想到的更加复杂.例如你想输入一个2维数组,然后累加里面所有的数,你总不可能去算吧?但是放在运行时计算也会让程序变慢,

这种一开始就能知道的值为什么我们不能在编译的时候算好呢?

模板元就能够达到这个效果.

  对于刚刚那个简单的相加的函数,我们可以给出简单的模板元函数

template<int x, int y>
struct fun{
const static int _ret_val = x + y;
}

assert(fun<100, 20>::_ret_val == 120);


  看,这样就可以很优雅地预先算好这个值

  好了,下面开始正题.解释我都写在代码里面的注释里,下面上代码

// Copyright (C) 2012/12/15 fish
//
//
//

#ifndef _FISH_ENDIAN_H_
#define _FISH_ENDIAN_H_

#ifdef _MSC_VER
#define IS_BIG_ENDIAN false
//#elif
//这里定义其他平台
//本人对除windows平台以外的平台不熟悉
//望有心人看到帮忙补充
//谢谢
#endif

struct check_endian{
const static bool _is_big_endian = IS_BIG_ENDIAN;
const static bool _is_little_endian = !IS_BIG_ENDIAN;
};

//字节顺序转换模板函数
template<unsigned int i>
struct _change_endian{

//分别取出1,2,3,4个字节,然后交换
const static unsigned int _i1 = i >> 24;
const static unsigned int _i2 = ((i << 8) >> 24) << 8;
const static unsigned int _i3 = ((i << 16) >> 24) << 16;
const static unsigned int _i4 = (i << 24);

const static unsigned int _ret_val = _i1 + _i2 + _i3 + _i4;
};

//////////////////////////////////////////////////////////////////////////
//转换为小端法
//其中有默认模板参数,使用了check_endian判断是哪种字节顺序
template<unsigned int i, bool _is_little_endian = check_endian::_is_little_endian>
struct to_little_endian_int32{

};

//发现本平台已经是小端法则什么也不做返回
template<unsigned int i>
struct to_little_endian_int32<i, true>{
const static unsigned int _ret_val = i;
};

//否则调用_change_endian转换字节顺序
template<unsigned int i>
struct to_little_endian_int32<i, false>{
const static unsigned int _ret_val = _change_endian<i>::_ret_val;
};
//////////////////////////////////////////////////////////////////////////

//////////////////////////////////////////////////////////////////////////
//转换为大端法
template<unsigned int i, bool _is_big_endian = check_endian::_is_big_endian>
struct to_big_endian_int32{

};

//发现本平台已经是大端法则什么也不做返回
template<unsigned int i>
struct to_big_endian_int32<i, true>{
const static unsigned int _ret_val = i;
};

//否则调用_change_endian转换字节顺序
template<unsigned int i>
struct to_big_endian_int32<i, false>{
const static unsigned int _ret_val = _change_endian<i>::_ret_val;
};
//////////////////////////////////////////////////////////////////////////

#endif //_FISH_ENDIAN_H_


  模板元非常忠实地帮我们计算出结果,善用模板元将会在大工程里面对我们有很大帮助.
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐