哎马,我天,我总算看懂它的源码了。汗。使用的时候能用data_type()获取类型(可以用enum的标记),data()获取数据。
我的schema是这个结构
// Example IDL file for our monster's schema.
namespace modrim;
table TextCmd {
msg_len:short;
name:string;
}
table GotoCmd {
goto_label:long;
name:string;
}
union Cmd {
text:TextCmd,
goto_cmd:GotoCmd
}
table Root {
data:[Cmd];
}
root_type Root;
最主要的是包含union的Vector。下面这个函数是最关键的函数。这个函数是生成器生成的。对应上面的Root
inline flatbuffers::Offset<Root> CreateRoot(
flatbuffers::FlatBufferBuilder &_fbb,
flatbuffers::Offset<flatbuffers::Vector<uint8_t>> data_type = 0,
flatbuffers::Offset<flatbuffers::Vector<flatbuffers::Offset<void>>> data = 0) {
RootBuilder builder_(_fbb);
builder_.add_data(data);
builder_.add_data_type(data_type);
return builder_.Finish();
}
union在函数里被分成两个部分,一个是类型data_type,一个是保存的数据data,放在两个Vector(flatbutters的Vector,注意类型)里面,创建的时候要一一对应创建。要注意data数组要注入的类型,接口是.Union()。
flatbuffers::FlatBufferBuilder builder;
std::vector<uint8_t> data_types;
std::vector<flatbuffers::Offset<void>> data;
auto cmd1 = CreateTextCmd(builder,312,builder.CreateString("woshiyigedaguaishou"));
auto cmd2 = CreateGotoCmd(builder,245,builder.CreateString("dddkeo"));
data_types.push_back(Cmd_text);//enum类型标记
data.push_back(cmd1.Union());//注入数据
data_types.push_back(Cmd_goto_cmd);//另一个enum类型标记
data.push_back(cmd2.Union());//注入另一个数据
auto vec_types = builder.CreateVector(data_types);
auto vec_data = builder.CreateVector(data);
auto root = CreateRoot(builder,vec_types,vec_data);
builder.Finish(root);
cout<<builder.GetSize()<<endl;//
//save
fstream outfile("test.bin",ios::out | ios::binary);
outfile.write((char*)builder.GetBufferPointer(), builder.GetSize());
outfile.close();
接下来就是读取数据了。
std::fstream infile;
infile.open("test.bin",ios::binary | ios::in);
if (!infile)
{
return 0;
}
infile.seekg(0, ios::end);
int length = (int)infile.tellg();
infile.seekg(0, ios::beg);
char* data = new char[length];
infile.read(data, length);
infile.close();
auto root = GetRoot(data);
cout<<(int)root->data_type()->Get(1)<<endl;//类型输出
cout<<root->data()->GetAs<GotoCmd>(1)->name()->c_str()<<endl;//已经知道第二个是goto指令,这里就直接转换了。
有两个接口data_type()获得保存类型标记的数组,data获得数据数组,然后就根据标记进行类型转换即可。