是否可以将平面缓冲区与 JSON 进行序列化/反序列化?
我真正想做的是将平面缓冲区保存为 JSON,允许人们更改他们想要的任何值,然后将 JSON 读回平面缓冲区(并在应用程序中以某种方式使用它)。
也许还有另一种方法可以达到同样的效果。我们正在使用 C++ 工作。
是的,这是 FlatBuffers 中的内置功能。请参阅此处的“文本和架构解析”:https://google.github.io/flatbuffers/flatbuffers_guide_use_cpp.html 另请参见
test.cpp
中的示例 ParseAndGenerateTextTest()
,或者也 registry.h
我用的就是这个
sample.fbs 文件包含平面缓冲区架构。
table sample
{
firstName: string;
lastName: string;
age: int;
}
root_type sample;
将 JSON 解析为 Flatbuffers 二进制并返回 JSON 的程序
#include <iostream>
#include <string>
#include "flatbuffers/idl.h"
int main()
{
std::string input_json_data = "{ \
firstName: \"somename\", \
lastName: \"someothername\", \
age: 21 \
} \
";
std::string schemafile;
std::string jsonfile;
bool ok = flatbuffers::LoadFile("sample.fbs", false, &schemafile);
if (!ok) {
std::cout << "load file failed!" << std::endl;
return -1;
}
flatbuffers::Parser parser;
parser.Parse(schemafile.c_str());
if (!parser.Parse(input_json_data.c_str())) {
std::cout << "flatbuffers parser failed with error : " << parser.error_ << std::endl;
return -1;
}
std::string jsongen;
if (!GenerateText(parser, parser.builder_.GetBufferPointer(), &jsongen)) {
std::cout << "Couldn't serialize parsed data to JSON!" << std::endl;
return -1;
}
std::cout << "intput json" << std::endl
<< input_json_data << std::endl
<< std::endl
<< "output json" << std::endl
<< jsongen << std::endl;
return 0;
}
产生以下输出
$ ./build/output/test_json_fb
intput json
{ firstName: "somename", lastName: "someothername", age: 21 }
output json
{
firstName: "somename",
lastName: "someothername",
age: 21
}
通过引用页面创建https://github.com/google/flatbuffers/blob/master/samples/sample_text.cpp
http://frogermcs.github.io/json-parsing-with-flatbuffers-in-android/
FlatBuffers 库最近越来越流行。如果你查看上一篇 Android 性能模式系列,Colt McAnlis 在不同的视频中多次提到它。您可能还记得 Facebook 关于迁移到 FlatBuffers 的公告。另外,前一段时间我发表了关于如何开始在 Android 中使用它的文章。
java
public class FlatBuffersParser {
static {
System.loadLibrary("FlatBuffersParser");
}
public ByteBuffer parseJson(String json, String schema) {
final byte[] bytes = parseJsonNative(json, schema);
return ByteBuffer.wrap(bytes);
}
private native byte[] parseJsonNative(String json, String schema);
}
**C++**
#ifndef __MAIN_H__
#define __MAIN_H__
#include <flatbuffers/idl.h>
#include "main.h"
JNIEXPORT jbyteArray JNICALL
Java_frogermcs_io_flatbuffersparser_FlatBuffersParser_parseJsonNative(JNIEnv *env,
jobject instance,
jstring json_,
jstring schema_) {
const char *json = env->GetStringUTFChars(json_, 0);
const char *schema = env->GetStringUTFChars(schema_, 0);
flatbuffers::Parser parser;
bool ok = parser.Parse(schema) && parser.Parse(json);
env->ReleaseStringUTFChars(json_, json);
env->ReleaseStringUTFChars(schema_, schema);
if (ok) {
flatbuffers::uoffset_t length = parser.builder_.GetSize();
jbyteArray result = env->NewByteArray(length);
uint8_t *bufferPointer = parser.builder_.GetBufferPointer();
env->SetByteArrayRegion(result, 0, length, reinterpret_cast<jbyte *>(bufferPointer));
return result;
}
}
#endif // __MAIN_H__
使用
flatc
命令可以将二进制文件转换为 JSON 文件。
flatc --json --raw-binary <flatbuffer_schema_file.fbs> -- <binary_file.bin>
有关更多信息,请查看 Flatbuffer 指南。
请注意,此命令可能不会产生任何输出。要解决此问题,您应该在 Flatbuffer 架构中声明根类型。要修复此问题,请在平面缓冲区架构中声明根类型。
root_type FOO;
Flatc 文档 提供了一个附加选项,用于使用
--root-type T
指定根类型