char或unsigned char给int赋值区别
2015-05-13 18:14:38
这段时间写了一个简单的游戏网络框架,里面套接字收发自己实现了一个Buffer,今天零散时间想实现一下Buffer提供read_int和write_int方法,大致代码如下
int buffer::read_int(void)
{
// 循环以BYTE位的方式填充整形
int value = _buffer[_start_offset++];
for (size_t i = 1; i < sizeof(int); i++) {
value = value << 8;
value |= _buffer[_start_offset++];
}
return value;
}
void buffer::write_int(int value)
{
// 循环以BYTE位的方式写入缓存
for (int i = sizeof(int)-1; i >= 0; i--)
_buffer[_valid_offset++] = ((value >> (i * 8)) & 0xFF);
}
首先先解释一下为什么要这样写,这样实现为了避免产生大小端问题,因为我们统一采用上面的读取和写入方法,肯定不会有大小端问题
这里简单解释一下大小端,若想详细了解,百度一下你会知道的更多,下面引用百度百科中的两句话
所谓的大端模式,是指数据的高字节,保存在内存的低地址中,而数据的低字节,保存在内存的高地址中
所谓的小端模式,是指数据的高字节保存在内存的高地址中,而数据的低字节保存在内存的低地址中
举个例子,可能会更好理解,请拿出桌面的计算器
十进制:4160486910 十六进制:F7FBFDFE 存储在小端的计算机中将是FEFDFBF7,数据的低字节是FE,保存在内存的低地址,由左至右就是由低到高,所以若是查看内存的话你首先看到的将是FE,当然大端正好是相反的。
接下来开始聊我今天碰到的问题,问题主要出在read_int中,就拿第一行代码举例说明,若_buffer[_start_offset++] = 0xF7,第一句执行的结果是 0xFFFFFFF7,若是仅看这一句当然也没有什么大问题,左移之后变成0xFFFFF700,假设此时_buffer[_start_offset++] = 0xFB,或运算之后就变成了0xFFFFFFFB,即便我用的是抑或运算,运算结果也是0x8FB,其实这样运算也并不是我想出来的,怎么就不对了呢,更何况我以前还用过,然后就是无穷无尽的测试。
其实这个时间我已经能说出来为什么出这样的问题啦,为什么第一行赋值的结果不是0x000000F7即0xF7
然后无意中发现这篇文章:http://bbs.csdn.net/topics/380177608
问题根源就是我_buffer用的是char 而不是unsigned char啊