thrift 中的 Union 显示在 c++ 中设置的所有值
Union in thrift shows all values setted in c++
我做了一个简单的三个字段的并集
union example{
1:string STRING,
2:i64 INT64,
3:double DOUBLE
}
然后我在客户端中将示例联合实例化为:
example ex;
ex.__set_STRING("Example");
ex.__isset.STRING = true;
并通过接受示例作为参数的方法发送示例
在服务器中,调用的方法是这样完成的:
void get(const example &ex)
{
cout << ex.__isset.STRING << ' ' << ex.__isset.INT64 << ' ' <<
ex.__isset.DOUBLE << endl;
cout << ex << endl;
}
奇怪的是,这样一个小程序的输出是:
1 1 1
example(STRING="Example", INT64=0, DOUBLE=0)
我不知道这是否是设置联合类型的正确方法,但我尝试了几种组合并且 none 似乎有效。
可在此处找到代码段的来源:https://github.com/enriquefynn/union_thrift
uint32_t type_ex::write(::apache::thrift::protocol::TProtocol* oprot) const {
uint32_t xfer = 0;
apache::thrift::protocol::TOutputRecursionTracker tracker(*oprot);
xfer += oprot->writeStructBegin("type_ex");
xfer += oprot->writeFieldBegin("STRING", ::apache::thrift::protocol::T_STRING, 1);
xfer += oprot->writeString(this->STRING);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldBegin("INT64", ::apache::thrift::protocol::T_I64, 2);
xfer += oprot->writeI64(this->INT64);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldBegin("DOUBLE", ::apache::thrift::protocol::T_DOUBLE, 3);
xfer += oprot->writeDouble(this->DOUBLE);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldStop();
xfer += oprot->writeStructEnd();
return xfer;
}
看起来像是联合的错误。这些值是无条件写入的,这适用于 struct
但不适用于 union
。因此,解决方法是添加一个明确的 optional
:
union type_ex
{
1 : optional string STRING,
2 : optional i64 INT64,
3 : optional double DOUBLE
}
这给了我们:
uint32_t type_ex::write(::apache::thrift::protocol::TProtocol* oprot) const {
uint32_t xfer = 0;
apache::thrift::protocol::TOutputRecursionTracker tracker(*oprot);
xfer += oprot->writeStructBegin("type_ex");
if (this->__isset.STRING) {
xfer += oprot->writeFieldBegin("STRING", ::apache::thrift::protocol::T_STRING, 1);
xfer += oprot->writeString(this->STRING);
xfer += oprot->writeFieldEnd();
}
if (this->__isset.INT64) {
xfer += oprot->writeFieldBegin("INT64", ::apache::thrift::protocol::T_I64, 2);
xfer += oprot->writeI64(this->INT64);
xfer += oprot->writeFieldEnd();
}
if (this->__isset.DOUBLE) {
xfer += oprot->writeFieldBegin("DOUBLE", ::apache::thrift::protocol::T_DOUBLE, 3);
xfer += oprot->writeDouble(this->DOUBLE);
xfer += oprot->writeFieldEnd();
}
xfer += oprot->writeFieldStop();
xfer += oprot->writeStructEnd();
return xfer;
}
我做了一个简单的三个字段的并集
union example{
1:string STRING,
2:i64 INT64,
3:double DOUBLE
}
然后我在客户端中将示例联合实例化为:
example ex;
ex.__set_STRING("Example");
ex.__isset.STRING = true;
并通过接受示例作为参数的方法发送示例
在服务器中,调用的方法是这样完成的:
void get(const example &ex)
{
cout << ex.__isset.STRING << ' ' << ex.__isset.INT64 << ' ' <<
ex.__isset.DOUBLE << endl;
cout << ex << endl;
}
奇怪的是,这样一个小程序的输出是:
1 1 1
example(STRING="Example", INT64=0, DOUBLE=0)
我不知道这是否是设置联合类型的正确方法,但我尝试了几种组合并且 none 似乎有效。
可在此处找到代码段的来源:https://github.com/enriquefynn/union_thrift
uint32_t type_ex::write(::apache::thrift::protocol::TProtocol* oprot) const {
uint32_t xfer = 0;
apache::thrift::protocol::TOutputRecursionTracker tracker(*oprot);
xfer += oprot->writeStructBegin("type_ex");
xfer += oprot->writeFieldBegin("STRING", ::apache::thrift::protocol::T_STRING, 1);
xfer += oprot->writeString(this->STRING);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldBegin("INT64", ::apache::thrift::protocol::T_I64, 2);
xfer += oprot->writeI64(this->INT64);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldBegin("DOUBLE", ::apache::thrift::protocol::T_DOUBLE, 3);
xfer += oprot->writeDouble(this->DOUBLE);
xfer += oprot->writeFieldEnd();
xfer += oprot->writeFieldStop();
xfer += oprot->writeStructEnd();
return xfer;
}
看起来像是联合的错误。这些值是无条件写入的,这适用于 struct
但不适用于 union
。因此,解决方法是添加一个明确的 optional
:
union type_ex
{
1 : optional string STRING,
2 : optional i64 INT64,
3 : optional double DOUBLE
}
这给了我们:
uint32_t type_ex::write(::apache::thrift::protocol::TProtocol* oprot) const {
uint32_t xfer = 0;
apache::thrift::protocol::TOutputRecursionTracker tracker(*oprot);
xfer += oprot->writeStructBegin("type_ex");
if (this->__isset.STRING) {
xfer += oprot->writeFieldBegin("STRING", ::apache::thrift::protocol::T_STRING, 1);
xfer += oprot->writeString(this->STRING);
xfer += oprot->writeFieldEnd();
}
if (this->__isset.INT64) {
xfer += oprot->writeFieldBegin("INT64", ::apache::thrift::protocol::T_I64, 2);
xfer += oprot->writeI64(this->INT64);
xfer += oprot->writeFieldEnd();
}
if (this->__isset.DOUBLE) {
xfer += oprot->writeFieldBegin("DOUBLE", ::apache::thrift::protocol::T_DOUBLE, 3);
xfer += oprot->writeDouble(this->DOUBLE);
xfer += oprot->writeFieldEnd();
}
xfer += oprot->writeFieldStop();
xfer += oprot->writeStructEnd();
return xfer;
}