今天被protocol buffer中的一个小问题坑了一大把,所以来记录下protocol buffer中的一些东东。
这次被坑就是因为枚举的问题,消息里面有个成员是个枚举变量,在给它赋值的时候直接强转赋值,而没有判断具体的值是否在枚举的范围内,于是乎程序直接宕机了。其实这个错误也不是第一次犯了,只怪这种错误太容易触发了,一不小心就忘了……
enum MyEm
{
MyEm_One = 1;
MyEm_Two = 2;
MyEm_Three = 3;
}
message MyMsg
{
optional MyEm em= 1;
}
int val=8;
MyMsg msg;
msg.set_em((MyEm)val);
在最后一句稳稳的宕机。对于这种情况我一般的做法就是把那个枚举变量改成int类型的,这样怎么赋值都不会有问题了,一劳永逸。
还有一点就是当在消息中有repeated字段而且repeated的量很大的时候,要尽量让repeated的变量是简单类型,例如在下面的例子中就应该尽量使用con2:
con1
message MySubMsg
{
optional uint32 mem1= 1;
optional uint32 mem2= 2;
}
message MyMsg
{
repeated MySubMsg mem= 1;
}
con2
message MyMsg
{
repeated uint32 mem1= 1;
repeated uint32 mem2= 2;
}
因为在protocol buffer底层对于repeated类型存储的是一个指针数组,对于简单类型就直接把值存入数组了,在数组size不足时就把size翻倍,也只是new了一次数组,但是如果存复杂类型的时候还需要new出来这个复杂类型对象,然后把指针存在数组中,这样要存多少对象就要new多少次,但是new的效率是很低的。