字节流例子
程序员文章站
2022-05-14 13:27:36
...
主要用于没法用struct的情况
模拟文件的读写方式
class bytes_stream
{
char * pBuffer;
unsigned int _write_pos;
unsigned int _read_pos;
unsigned int _size;
int read_or_write;
public:
enum {READ=1, WRITE};
bytes_stream(char* p, unsigned int buffsize, int readOrWrite):
pBuffer(p),_write_pos(0),_read_pos(0)
,_size(buffsize),read_or_write(readOrWrite){
}
~bytes_stream(){
}
void reset(char * p , unsigned int buffsize, int readOrWrite){
pBuffer = p;
_write_pos = 0;
_read_pos = 0;
_size = buffsize;
read_or_write = readOrWrite;
}
unsigned writePos() const {
return _write_pos;
}
unsigned readPos() const{
return _read_pos;
}
bool readInt8(int8_t * data){
return readData(data);
}
bool readInt16(int16_t * data){
return readData(data);
}
bool readInt32(int32_t * data){
return readData(data);
}
bool readInt64(int64_t * data){
return readData(data);
}
bool readFloat(float * data){
return readData(data);
}
double readDouble(double * data){
return readData(data);
}
//读基础类型数据, 返回是否成功, data用于存放数据
template <typename T>
bool readData(T *data){
if(!pBuffer || !data)
return false;
if((read_or_write & READ) && (_read_pos + sizeof(T) <= _size)){
memcpy(data,pBuffer+_read_pos , sizeof(T));
_read_pos += sizeof(T);
return true;
}
return false;
}
//写基础类型数据
template <typename T>
bool writeData(T data){
if(!pBuffer)
return false;
if((read_or_write & WRITE) && _write_pos + sizeof(T) <= _size){
memcpy(pBuffer+_write_pos , &data,sizeof(T));
_write_pos += sizeof(T);
return true;
}
return false;
}
//char
bool writeInt8(int8_t data){
return writeData(data);
}
//short
bool writeInt16(int16_t data){
return writeData(data);
}
//int
bool writeInt32(int32_t data){
return writeData(data);
}
//long long
bool writeIn64(int64_t data){
return writeData(data);
}
bool writeFloat(float data){
return writeData(data);
}
bool writeDouble(double data){
return writeData(data);
}
//写入数组, 我就不扩展其他类型了,需要的自己加
// 返回是否成功, 参数arr : 要写入哪个数组, n : 数组长度
template <typename T>
bool writeArr(const T * arr , unsigned int n){
if(!pBuffer)
return false;
auto totallen = sizeof(T) * n;
if(( (read_or_write & WRITE) && _write_pos + totallen+ sizeof(n)) <= _size){
// 先写入数组的长度,这样以后读取数组就知道该读多少字节的数组
if(writeData(n)){
memcpy(pBuffer + _write_pos ,arr , totallen);
_write_pos += totallen;
return true;
}
}
return false;
}
//读数组
//返回读取到的数组长度 , 参数 arr: 读到哪个缓冲区, arrlen : 此arr长度是多少
template <typename T>
unsigned int readArr(T * arr , unsigned int arrlen){
if(!pBuffer || !arr)
return 0;
unsigned int n = 0;
//读取数组长度
if( !readData(&n) )
return 0;
//如果不够容纳
if( arrlen < n){
_read_pos -= sizeof(n);
return 0;
}
auto totallen = n * sizeof(T);
if( _read_pos + totallen <= _size && (read_or_write & READ)){
memcpy(arr,pBuffer + _read_pos , totallen);
_read_pos += totallen;
return n;
}
else {
_read_pos -= sizeof(n);
}
return 0;
}
};
int main(int argc, char* argv[])
{
char * p = new char[1024];
memset(p,0,1024);
bytes_stream a(p,1024,bytes_stream::WRITE|bytes_stream::READ);
const char * str = "123";
cout << "begin write" << endl;
a.writeArr(str,strlen(str));
a.writeInt8(1);
a.writeInt16(2);
a.writeInt32(32);
cout << "writepos:" <<a.writePos() << endl;
int b[] = {1,2,3};
a.writeArr(b,3);
cout << "writepos:" <<a.writePos() << endl;
cout << "begin read" << endl;
char * readarr = new char[100];
unsigned int nlen = a.readArr(readarr,100);
readarr[nlen] = 0;
cout << "arr len : " << nlen << ", readarr:" << readarr << endl;
int data = 0;
a.readInt8((signed char*)&data);
cout << "readint8 : " <<data << endl;
a.readInt16((short *)&data);
cout << "readint16 :" << data<<endl;
a.readInt32(&data);
cout << "readint32 :" << data << endl;
int * readarr2 = new int[10];
nlen = a.readArr(readarr2,10);
cout << "read int arr , len:" << nlen << endl;
for(int i = 0; i < nlen ; ++i)
cout << readarr2[i] << endl;
cout << endl;
cout << "read pos:" << a.readPos() << endl;
return 0;
}
下一篇: JAVA 操作防抖(非RxJava方案)