Berkeley DB——Store Structure
Berkeley DB——Store Structure
Introduction
Berkeley DB适合存储简单的数据,比如那些c/c++定义的类型,诸如int、float、char和wchar_t等等。因为DB虽然可以存入任意类型的数据,但是它只会原原本本按照字节将数据存入(entirely 8-bit clean data),其它的工作需要我们自己负责。
如果我们定义了一个只包含简单数据类型属性的结构体,且我们给这个结构体对象赋值的时候,每个属性都不是动态分配内存的,那我们直接使用Db::put方法可以将其存入数据库中,且简单的Db::get后强制转换就能将其还原出来——可是这在实际开发中几乎是不可能的。所以在将structure object存入DB的时候我们需要做更多的工作——我们需要将这个对象转换为字节数组unsigned char的array,然后再存入DB中;get数据的时候需要将这个array再还原为我们的structure object,有术语来指明它们:marshalling和un-marshalling。除此之外,还有一个办法,就是使用二进制的序列化和反序列化。
Marshalling and Un-marshalling
这是一种比较麻烦的办法,也是一种非常不灵活,不美观的方式,但是它是有效的。
使用run-length的方式——先将属性的长度存入array中,然后再将此属性使用内存拷贝的方式存入array;还原的时候先取得长度,然后根据此长度得到此属性的值。例子:
struct MyStruct { wchar_t* Name; wchar_t* Description;
unsigned int GetSize() { unsigned int size = 0; size += sizeof(size); size += wcslen(Name)*2+2; size += sizeof(size); size += wcslen(Description)*2+2; return size; } //Marshall the struct to a run-length byte array unsigned int { size_t bytesCount=GetSize(); size_t len = 0; unsigned char *p; memset(buffer,0,bytesCount); p = &buffer[0]; //Name len = wcslen(Name)*2+2; memcpy(p,&len,sizeof(len));//id length p+=sizeof(len); memcpy(p,Name,len); p+=len; //description len = wcslen(Description)*2+2; memcpy(p,&len,sizeof(len));//id length p+=sizeof(len); memcpy(p,Description,len); p+=len; return bytesCount; } //Unmarshall the byte array to struct void Unmarshall(unsigned char* buffer) { unsigned char* p; size_t len = 0; p = &buffer[0]; //Name memcpy(&len,p,sizeof(len)); p+= sizeof(len); Name = (wchar_t*)malloc(len); memcpy(Name,p,len); p+= len; //Description memcpy(&len,p,sizeof(len)); p+= sizeof(len); Description = (wchar_t*)malloc(len); memcpy(Description,p,len); p+= len; } }; |
使用Marshall来得到byte array,将此byte array存入DB。而从DB中get到byte array后,只需要使用Unmarshall方法就可以还原该structure object了。缺点显而易见:如果的struct变动了,多处代码都需要变动,代码比较繁复冗长,特别是当struct的属性比较多的时候。
Serialization and Un-serialization
序列化和反序列化已经是普遍使用的技术了,我们可以使用该技术将对象转换为byte array(或者text),和将byte array(或者text)还原为对象。序列化和反序列化的方法有很多,根据实际情况选择合适的方法。
Ref:
Serialization and Unserialization