Git Product home page Git Product logo

xpack's Introduction

xpack

English

  • 用于在C++结构体和json/xml/yaml/bson/mysql/sqlite之间互相转换
  • 只有头文件, 无需编译库文件,所以也没有Makefile。
  • 支持bson,依赖于libbson-1.0,需自行安装。未经充分测试,具体请参考README
  • 支持MySQL,依赖于libmysqlclient-dev,需自行安装。未经充分测试
  • 支持Sqlite,依赖于libsqlite3,需自行安装。未经充分测试
  • 支持yaml,依赖于yaml-cpp,需自行安装。未经充分测试
  • 具体可以参考example的例子

基本用法

  • 结构体后面用XPACK宏包含各个变量,XPACK内还需要一个字母,不同字母的意义请参考FLAG
  • 用xpack::json::encode把结构体转json
  • 用xpack::json::decode把json转结构体
#include <iostream>
#include "xpack/json.h" // Json包含这个头文件,xml则包含xpack/xml.h

using namespace std;

struct User {
    int id;
    string  name;
    XPACK(O(id, name)); // 添加宏定义XPACK在结构体定义结尾
};

int main(int argc, char *argv[]) {
    User u;
    string data = "{\"id\":12345, \"name\":\"xpack\"}";

    xpack::json::decode(data, u);          // json转结构体
    cout<<u.id<<';'<<u.name<<endl;

    string json = xpack::json::encode(u);  // 结构体转json
    cout<<json<<endl;

    return 0;
}

容器支持

目前支持下列容器(std)

  • vector
  • set
  • list
  • map<string, T>
  • map<integer, T> // 仅JSON,XML不支持
  • unordered_map<string, T> (需要C++11支持)
  • shared_ptr (需要C++11支持)

FLAG

宏XPACK里面,需要用字母将变量包含起来,比如XPACK(O(a,b)),XPACK可以包含多个字母,每个字母可以包含多个变量。目前支持的字母有:

  • X。格式是X(F(flag1, flag2...), member1, member2,...) F里面包含各种FLAG,目前支持的有:
    • 0 没有任何FLAG
    • OE omitempty,encode的时候,如果变量是0或者空字符串或者false,则不生成对应的key信息
    • EN empty as null, 用于json的encode,OE是直接不生成empty的字段,EN则是生成一个null
    • M mandatory,decode的时候,如果这个字段不存在,则抛出异常,用于一些id字段。
    • ATTR attribute,xml encode的时候,把值放到attribute里面。
    • SL single line, json encode的时候,对于数组,放在一行里面
  • C。格式是C(customcodec, F(flag1,flags...), member1, member2,...)用于自定义编解码函数,详情请参考自定义编解码
  • O。等价于X(F(0), ...) 没有任何FLAG。
  • M。等价于X(F(M),...) 表示这些字段是必须存在的。
  • A。别名,A(member1, alias1, member2, alias2...),用于变量和key名不一样的情况
  • AF。带FLAG的别名,AF(F(flag1, flag2,...), member1, alias1, member2, alias2...)
  • B。位域,B(F(flag1, flag2, ...), member1, member2, ...) 位域不支持别名
  • I。继承,I(baseclass1, baseclass2....),里面放父类
  • E。枚举:
    • 如果编译器支持C++11,不需要用E,枚举可以放X/O/M/A里面。
    • 否则枚举只能放E里面,不支持别名

别名

  • 用于变量名和key名不一致的场景
  • 格式是A(变量,别名....)或者AF(F(flags), 变量,别名....),别名的格式是"x t:n"的格式
    • x表示全局别名,t表示类型(目前支持json、xml、bson),n表示类型下的别名
    • 全局别名可以没有,比如json:_id是合法的
    • 类型别名可以没有,比如_id是合法的
    • 有类型别名优先用类型别名,否则用全局别名,都没有,则用变量名
#include <iostream>
#include "xpack/json.h"

using namespace std;

struct Test {
    long uid;
    string  name;
    XPACK(A(uid, "id"), O(name)); // "uid"的别名是"id"
};

int main(int argc, char *argv[]) {
    Test t;
    string json="{\"id\":123, \"name\":\"Pony\"}";

    xpack::json::decode(json, t); 
    cout<<t.uid<<endl;
    return 0;
}

位域

  • 使用"B"来包含位域变量,位域不支持别名
#include <iostream>
#include "xpack/json.h"

using namespace std;

struct Test {
    short ver:8;
    short len:8;
    string  name;
    XPACK(B(F(0), ver, len), O(name)); 
};

int main(int argc, char *argv[]) {
    Test t;
    string json="{\"ver\":4, \"len\":20, \"name\":\"IPv4\"}";

    xpack::json::decode(json, t);
    cout<<t.ver<<endl;
    cout<<t.len<<endl;
    return 0;
}

继承

  • 使用"I"来包含父类。需要用到父类的变量就包含,用不到可以不包含。
  • 父类的父类也需要包含,比如class Base; class Base1:public Base; class Base2:public Base1;那么在Base2中需要I(Base1, Base)
  • 父类也需要定义XPACK/XPACK_OUT宏。
#include <iostream>
#include "xpack/json.h"

using namespace std;

struct P1 {
    string mail;
    XPACK(O(mail));
};

struct P2 {
    long version;
    XPACK(O(version));
};

struct Test:public P1, public P2 {
    long uid;
    string  name;
    XPACK(I(P1, P2), O(uid, name)); 
};

int main(int argc, char *argv[]) {
    Test t;
    string json="{\"mail\":\"[email protected]\", \"version\":2019, \"id\":123, \"name\":\"Pony\"}";

    xpack::json::decode(json, t);
    cout<<t.mail<<endl;
    cout<<t.version<<endl;
    return 0;
}

枚举

  • 如果编译器支持C++11,则枚举和普通变量名一样,放X/O/M/A里面皆可。
  • 否则需要放到E里面,格式是E(F(...), member1, member2, ...)
#include <iostream>
#include "xpack/json.h"

using namespace std;

enum Enum {
    X = 0,
    Y = 1,
    Z = 2,
};

struct Test {
    string  name;
    Enum    e;
    XPACK(O(name), E(F(0), e)); 
};

int main(int argc, char *argv[]) {
    Test t;
    string json="{\"name\":\"IPv4\", \"e\":1}";

    xpack::json::decode(json, t);
    cout<<t.name<<endl;
    cout<<t.e<<endl;
    return 0;
}

自定义编解码

应用场景

  • 有些基础类型想用自定义方式编码,比如用字符串的方式来编码整数/浮点数
  • 部分类型可能不想按结构体变量逐个编码,比如定义了一个时间结构体:
struct Time {
    long ts; //unix timestamp
};

并不希望编码成{"ts":1218196800} 这种格式,而是希望编码成"2008-08-08 20:00:00"这种格式。

这里有两种方式:

  • 使用xtype,可以参考例子
  • 用C来包含需要自定义编解码的变量(下面简称C方法),可以参考例子

两种方法本质上都是自己去实现encode/decode,但是有以下区别:

  • xtype是类型级别的,也就是一旦某个类型用xtype封装之后,那么自定义的encode/decode就对这个类型生效。xtype无法作用于基本类型(int/string等)
  • C方法能支持基本类型(int/string等)和非基本类型,但是仅作用于用C包含的变量,比如int a;int b; O(a), C(custome_int, F(0), b);那么a还是用默认的编解码,b才是用自定义的编解码。
  1. xtype优先于XPACK宏,也就是定义了xtype的,会优先使用xtype的encode/decode
  2. C方法优先于xtype,也就是用C包含的变量,一定会用C里面指定的编解码方法。

用这两个特性,可以实现一些比较灵活的编解码控制,比如这个例子实现了一个根据变量情况来编码的功能,如果Sub.type==1则encode seq1,否则encode seq2. __x_pack_decode__x_pack_encode是XPACK宏给结构体添加的decode/encode函数,自定义编解码函数可以通过这些函数调用xpack默认的编解码功能。

union

可以使用自定义编解码来处理联合体,可以参考范例

数组

  • decode的时候如果元素个数超过数组的长度,会截断
  • char数组按有\0结束符处理
#include <iostream>
#include "xpack/json.h"

using namespace std;


struct Test {
    char  name[64];
    char  email[64];
    XPACK(O(name, email)); 
};

int main(int argc, char *argv[]) {
    Test t;
    string json="{\"name\":\"Pony\", \"email\":\"[email protected]\"}";

    xpack::json::decode(json, t);
    cout<<t.name<<endl;
    cout<<t.email<<endl;
    return 0;
}

不定类型

  • 用于json的schema不确定的场景
  • xpack::JsonData来接收这些信息
  • 可以参考例子
  • xpack::JsonData主要的方法有:
    • Type。用于获取类型
    • IsXXX系列函数。用于判断是否是某种类型,基本等价于return Type()==xxxx;
    • GetXXX系列函数。用来提取值。
    • 重载bool。用来判断是否是一个合法的JsonData。
    • Size。用于数组类型判断元素的个数
    • operator [](size_t index) 用来取数组的第index个元素(从0开始)
    • operator [](const char *key) 用来根据key取Object类型的元素
    • Begin。用来遍历Object的元素,取第一个。
    • Next。配合Begin使用,获取下一个元素。
    • Key。配置Begin和Next使用,遍历的时候获取Key

第三方类和结构体

  • 用XPACK_OUT而非XPACK来包含变量
  • XPACK_OUT必须定义在全局命名空间
#include <sys/time.h>
#include <iostream>
#include "xpack/json.h"

using namespace std;

/*
struct timeval {
    time_t      tv_sec;
    suseconds_t tv_usec;
};
*/

// timeval is thirdparty struct
XPACK_OUT(timeval, O(tv_sec, tv_usec));

struct T {
    int  a;
    string b;
    timeval t;
    XPACK(O(a, b, t));
};


int main(int argc, char *argv[]) {
    T t;
    T r;
    t.a = 123;
    t.b = "xpack";
    t.t.tv_sec = 888;
    t.t.tv_usec = 999;
    string s = xpack::json::encode(t);
    cout<<s<<endl;
    xpack::json::decode(s, r);
    cout<<r.a<<','<<r.b<<','<<r.t.tv_sec<<','<<r.t.tv_usec<<endl;
    return 0;
}

格式化缩进

  • encode缺省生成的json/xml是没有缩进的,适合程序使用,如果让人读,可以进行缩进。
  • encode的最后两个参数控制
    • indentCount 表示缩进的字符数,<0表示不缩进,0则是换行但是不缩进
    • indentChar 表示缩进的字符,用空格或者制表符

XML数组

  • 数组默认会用变量名作为元素的标签,比如"ids":[1,2,3],对应的xml是:
<ids>
    <ids>1</ids>
    <ids>2</ids>
    <ids>3</ids>
</ids>
  • 可以用别名的方式来控制数组的元素的标签,比如A(ids,"xml:ids,vl@id"),vl后面跟着一个@xx,xx就是数组的标签,生成的结果就是:
<ids>
    <id>1</id>
    <id>2</id>
    <id>3</id>
</ids>
  • 如果希望数组直接展开,而不是在外面包一层,可以用别名加"sbs"的flag来实现,比如A(ids, "xml:ids,sbs"),注意,sbs标签仅能用于数组,其他地方使用可能会崩溃
<ids>1</ids>
<ids>2</ids>
<ids>3</ids>

CDATA

  • 对于CDATA类型,需要用"cdata"的flag来实现,比如A(data, "xml:data,cdata")
  • cdata只能用std::string来接收
  • 如果变量对应的xml不是CDATA结构,会按普通字符串来处理比如<data>hello</data>也可以解析成功

Qt支持

  • 修改config.h,开启XPACK_SUPPORT_QT这个宏(或者在编译选项开启)
  • 当前支持 QString/QMap/QList/QVector

MySQL

  • 目前仅支持decode,还不支持encode
  • 未经过完整测试,使用需要谨慎
  • 当前支持类型有:
    • string。简单测试。
    • 整型。简单测试。
    • 浮点型。未测试。
    • 用整型(比如time_t)接收TIME/DATETIME/TIMESTAMP。未测试。
    • 自定义类型转换,is_xpack_mysql_xtype,类似于xtype。未测试。
  • api有两个(xpack::mysql::) :
    • static void decode(MYSQL_RES *result, T &val)
      • 用来将MYSQL_RES转成结构体或者vector<>,如果是非vector,则只转换第一个row
    • static void decode(MYSQL_RES *result, const std::string&field, T &val)
      • 用来解析某个字段,用于只想获得某个字段内容的场景,比如select id from mytable where name = lilei,只想获得id信息。val支持vector

重要说明

  • 变量名尽量不要用__x_pack开头,不然可能会和库有冲突。
  • vc6不支持。
  • msvc没有做很多测试,只用2019做过简单测试。
  • json的序列化反序列化用的是rapidjson
  • xml的反序列化用的是rapidxml
  • xml的序列化是我自己写的,没有参考RFC,可能有和标准不一样的地方.
  • 有疑问可以加QQ群878041110

xpack's People

Contributors

freehawkzk avatar gongxiangshun avatar kevin-ren97 avatar willkk avatar xiezhaokai avatar xyz347 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

xpack's Issues

解析Json时,是否添加对UTF8-Bom文件的支持

是否能添加对UTF8-Bom文件的支持 xpack\json_decoder.h

 JsonDecoder(const std::string& str, bool isfile=false):xdoc_type(NULL, ""),_doc(new rapidjson::Document),_val(_doc) {
    std::string err;
    std::string data;

    do {
        if (isfile) {
            std::ifstream fs(str.c_str(), std::ifstream::binary);
            if (!fs) {
                err = "Open file["+str+"] fail.";
                break;
            }
            std::string _tmp((std::istreambuf_iterator<char>(fs)), std::istreambuf_iterator<char>());


            if (_tmp[0] == '\xEF' && _tmp[1] == '\xBB' && _tmp[2] == '\xBF')//if this formate is utf8-bom
            {
                data = _tmp.substr(3, _tmp.length() - 3);
            }
            else
            {
                data.swap(_tmp);
            }


            _doc->Parse(data);
        } else  {
            _doc->Parse(str);
        }

Is it possible to add support for enum key based std::map?

Currently Im using the following workaround.

// std::map<enum, T>
template <typename TK, typename TV>
struct is_xpack_xtype<std::map<TK, TV>> {
    static bool const value = true;
};

template <class OBJ, typename TK, typename TV>
bool xpack_xtype_decode(OBJ& obj, const char* key, std::map<TK, TV>& val, const Extend* ext) {
    if constexpr (std::is_enum_v<TK>) {
        std::map<int64_t, TV> tmp;
        if (!obj.decode(key, tmp, ext)) {
            return false;
        }
        val.clear();
        for (auto&& item : tmp) {
            val[item.first] = item.second;
        }
        return true;
    } else {
        static_assert(false, "std::map with this key type is not supported to decode");
        return false;
    }
}

template <class OBJ, typename TK, typename TV>
bool xpack_xtype_encode(OBJ& obj, const char* key, const std::map<TK, TV>& val, const Extend* ext) {
    if constexpr (std::is_enum_v<TK>) {
        std::map<TK, TV> tmp;
        for (auto&& item : val) {
            tmp[item.first] = item.second;
        }
        return obj.encode(key, tmp, ext);
    } else {
        static_assert(false, "std::map with this key type is not supported to encode");
        return false;
    }
}

解析map嵌套结构体bug

map的value类型是结构体,解析有问题。
示例:

struct value {
  int a;
  XPACK(O(a));
};
std::map<std::string, value>  map;
xpack::json::decode("{\"123\":{\"a\":1011}, \"234\":{}}", map);
cout << map.size() << ',' << map["123"].a << ',' << map["234"].a << endl;

后面空的234的a跟前面123里面的a值一样,看起来是内部实现复用了结构体成员。

xhas

请问原来x2struct中提供的xhas()方法在xpack中是否有替代函数?

后面是否考虑支持std::optional,开发者可通过判成员是否为std::nullopt,达到类似调用xhas()的目的。

util.h报错

错误提示:错误 C4146 一元负运算符应用于无符号类型,结果仍为无符号类型 \xpack\util.h 89

int64_t encode 结果有问题

struct JanusResponse {
	std::string janus;
	std::string transaction;		
	int64_t session_id = -1;
	int64_t sender = -1;
	XPACK(O(janus, transaction, session_id, sender));
};

struct CreateSessionData {
	int64_t id;
	XPACK(O(id));
};

struct CreateSessionResponse : public JanusResponse {
	CreateSessionData data;
	XPACK(I(JanusResponse), O(data));
};

std::string js = "{\"janus\":\"success\",\"transaction\":\"RftQMdXKkq6q\",\"data\":{\"id\":6053426257610390}}";
vi::CreateSessionResponse model;
xpack::json::decode(js, model);

std::string result = xpack::json::encode(model);

你好,我发现decode结果是对的,encode的结果是错的,id的值不对。是我的用法不对?
(在x2struct上能正确encode)

decode错误时提示Error类型

是否考虑在decode出错时增加 Error Enum 类型。来表示诸如 "值类型错误/ErrorValueType",“缺少必须的域/MissingmandatoryFiled”等解析错误?

或者将rapidxml/rapidJson 解析时的返回值透传回来,类似如下

 bool isSuccess = false;
    try
    {
        isSuccess = xpack::json::decode(content.toStdString(), j);
    }
    catch (const std::exception& e)
    {
        LOGERROR("decode error ");
    }

    return isSuccess;

extend.h报错

error:xpack\extend.h(47): error C2039: “set”: 不是“std”的成员
solution:include

windows 10, VS2017 x64

union支持情况

您好 请问XPACK是否支持union类型变量 如果不支持 有什么替代解决方案 非常感谢

enum class Enum : int64_t解析会出错

enum class Enum : int64_t 类型的枚举解析会出错,解析出来是个很大的值, 如果是enum class Enum : int 不会出错,是哪里的bug 吗

能否加一下xpack::json::decode(rapidjson::Value*, T&)

json.h中有decode(std::string&, T&),可以满足字符串到对象的解析。但在实际应用中,可能需要对复杂结构体中的部分Value对象解析到Object中。参考现有代码,加起来应该比较简单,比如:

    template <class T>
    static void decode(const rapidjson::Value* value_data, T &val) {
        JsonDecoder doc(value_data);
        doc.decode(NULL, val, NULL);
    }

结构体重命名

项目主页上介绍了怎么对结构体的成员变量重命名 那是否可以对结构体重命名呢

struct TimeSpan
{
    string startTime;
    string endTime;
    XPACK(O(startTime, endTime));
};
struct CMSearchDescription
{
    string           searchID;
    vector<TimeSpan> timeSpanList;
    XPACK(O(searchID, timeSpanList))
};

在最后的xml中,结构体TimeSpan对应的是timeSpan标签,我又不想在代码中将结构体名改为timeSpan,有什么办法吗

含转义符 string encode结果格式错误

elidedText 字段原文: ヽ市キ華虐蒙i川 鯨 | 根据 《幼ブL\n‐\ぷ弄始吋同: | 九、写―写。 | 替\niSBヽ 978-7-53,4-6579
Encode 结果:
{
"elidedText": "ヽ市キ華虐蒙i川 鯨 | 根据 《幼ブL\n‐\ぷ弄始吋同: | 九、写―写。 | 替\niSBヽ 978-7-53,4-6579"
}
错误: 转义符未进行处理
修复:
writer.h 442行添加
else if (escape[static_cast(c)] == '\') {
PutUnsafe(*os_, '\');
}

空数组出错

json文本为:{"data":{"info":[]}}时,解析会出错。在document.h的IsArray出错。
struct Info
{
int base, Id;
XPACK(O(base, Id));
};
struct dataInfo
{
std::vector data;
XPACK(O(data));
};
dataInfo sInfo;
xpack::json::decode("{"data":{"info":[]}}", sInfo);

return-statement with a value, in function returning ‘void’

json.h:39:82: error: return-statement with a value, in function returning ‘void’ [-fpermissive]
39 | return XDecoder(NULL, (const char*)NULL, node).decode(val, NULL);

there is a error of json.h,
image
the template function return a bool value, but the description of function return void.

clang 16.0.0-x86_64-pc-windows-msvc下编译不过

问题如题.
在windows下,使用 clang 16.0.0-x86_64-pc-windows-msvc编译报错.
报错信息如下:

[build] 正在启动生成
[proc] 执行命令: chcp
[proc] 执行命令: "D:\Program Files\CMake\bin\cmake.EXE" --build d:/temp/xpack-clang/build --config Debug --target all --
[build] [1/2  50% :: 0.683] Building CXX object CMakeFiles/xpack-clang.dir/main.cpp.obj
[build] FAILED: CMakeFiles/xpack-clang.dir/main.cpp.obj 
[build] C:\LLVM\bin\clang++.exe  -ID:/temp/xpack-clang/include/xpack -g -Xclang -gcodeview -O0 -D_DEBUG -D_DLL -D_MT -Xclang --dependent-lib=msvcrtd -MD -MT CMakeFiles/xpack-clang.dir/main.cpp.obj -MF CMakeFiles\xpack-clang.dir\main.cpp.obj.d -o CMakeFiles/xpack-clang.dir/main.cpp.obj -c D:/temp/xpack-clang/main.cpp
[build] D:/temp/xpack-clang/main.cpp:9:3: error: use of undeclared identifier 'X_PACK_L1_ENCODE'
[build]   XPACK(M(age, name));
[build]   ^
[build] D:/temp/xpack-clang/include/xpack/xpack.h:191:45: note: expanded from macro 'XPACK'
[build]     X_PACK_ENCODE_BEGIN X_PACK_N(X_PACK_L1, X_PACK_L1_ENCODE, __VA_ARGS__) return __x_pack_ret; }
[build]                                             ^
[build] D:/temp/xpack-clang/include/xpack/xencoder.h:150:16: note: in instantiation of function template specialization 'xpack::XEncoder<xpack::JsonWriter>::encode_struct<person>' requested here
[build]         return encode_struct(key, val, ext);
[build]                ^
[build] D:/temp/xpack-clang/include/xpack/json_encoder.h:273:12: note: in instantiation of function template specialization 'xpack::XEncoder<xpack::JsonWriter>::encode<person>' requested here
[build]         en.encode(NULL, val, NULL);
[build]            ^
[build] D:/temp/xpack-clang/include/xpack\json.h:50:19: note: in instantiation of function template specialization 'xpack::JsonEncoder::encode<person>' requested here
[build]         return en.encode(val);
[build]                   ^
[build] D:/temp/xpack-clang/main.cpp:17:29: note: in instantiation of function template specialization 'xpack::json::encode<person>' requested here
[build]   std::cout << xpack::json::encode(p) << std::endl;
[build]                             ^
[build] 1 error generated.
[build] ninja: build stopped: subcommand failed.
[proc] 命令“"D:\Program Files\CMake\bin\cmake.EXE" --build d:/temp/xpack-clang/build --config Debug --target all --”已退出,代码为 1
[driver] 生成完毕: 00:00:00.753
[build] 生成已完成,退出代码为 1

xpack.h中vscode显示该宏X_PACK_L1_ENCODE是启用的 请问该如何解决?

customize basetype's serialisation

Dear developer,
How could I do if I wanna to customize basetype's serialisation? For example, if I want to convert an int to its hex string representation during serialize or deserialize, current xtype.cpp cannot do this, its just warning "already defined" when I write template.
Any suggestions well be welcome.

容器限制

为什么没在设计中看到有关于容器限制相关,实际生产中一些string stl等 异常报文也是要重点考虑的呢

Silent error with overflowed integer

Hello,

Thanks for this great library. While using it, I encounterd an error with overflowed integer. I was able to reproduce this on json-data.cpp with a large integer.

* limitations under the License.
*/

#include <iostream>
#include "xpack/json.h"
#include <string>

using namespace std;

struct Example {
    string type;
    xpack::JsonData data;
    XPACK(O(type, data));
};

struct Range {
    int min;
    int max;
    XPACK(O(min, max));
};

struct User {
    int id;
    string name;
    XPACK(O(id, name));
};

static void test(const std::string &data) {
    Example e;
    xpack::json::decode(data, e);
    if (e.type == "range") {
        Range r;
        e.data.Get(r);
    } else if (e.type == "user") {
	User u;
	e.data.Get(u);
	cout << u.id << endl;
    } else {

    }

}

int main(int argc, char *argv[]) {
    (void)argc;
    (void)argv;

    string s1 = "{\"type\":\"range\", \"data\":{\"min\":12, \"max\":33}}";
    string s2 = "{\"type\":\"user\", \"data\":{\"id\":123344343434343435, \"name\":\"xpack\"}}";
    test(s1);
    test(s2);
    
    return 0;
}

With a large number in the id of s2, no error was reported (I tried with a larger number and an error indicting not integer is given, which I think should be the correct behavior), but the output is -545967093.

I'm using the latest version of the library on Ubuntu 20.04LTS.

请教一个继承的问题

两个struct属继承关系

struct A {
    string t1;
    XPACK(O(t1));
};

struct B : public A{
    string t2;
    XPACK(I(A), O(t2));
};

现在我有一个函数,接受的是A类型,但传递的是B类型,转成JSON字符串后B类型的数据丢了?

VOID invoke(A a)
{
    string data = xpack::json::encode(a); // data 没有 t2 ?
}

B b = {0};
b.t1 = "111";
b.t2 = "222";

invoke(b);

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.