当前位置: 首页 > article >正文

protobuf: 通讯录2.2

1.proto3

4.Any

其实也是一个.proto文件中的message类型(protobuf内置的)。

用的时候需要导入:

作用:可以存储任意消息类型,类似于面向对象编程中的多态

生成的Any字段方法:

public:

  // .google.protobuf.Any data = 4;
  bool has_data() const;
  private:
  bool _internal_has_data() const;
  public:
  void clear_data();
  const ::PROTOBUF_NAMESPACE_ID::Any& data() const;
  PROTOBUF_NODISCARD ::PROTOBUF_NAMESPACE_ID::Any* release_data();
  ::PROTOBUF_NAMESPACE_ID::Any* mutable_data();
  void set_allocated_data(::PROTOBUF_NAMESPACE_ID::Any* data);

解释:

has_data() 方法:判断当前data是否已经被赋值

mutable_data()方法:得到返回值为Any类型的指针,这类⽅法会为我们开辟好空间,可以直接对这块空间的内容进⾏修改。

库中的Any字段本身方法:

class PROTOBUF_EXPORT Any final : public ::PROTOBUF_NAMESPACE_ID::Message {
bool PackFrom(const ::PROTOBUF_NAMESPACE_ID::Message& message) {
...
}
bool UnpackTo(::PROTOBUF_NAMESPACE_ID::Message* message) const {
...
}
template<typename T> bool Is() const {
return _impl_._any_metadata_.Is<T>();
}
};

解释:

PackFrom() ⽅法可以将任意消息类型转为 Any 类型。

UnpackTo() ⽅法可以将 Any 类型转回之前设置的任意消息类型。

Is() ⽅法可以⽤来判断存放的消息类型是否为 typename T。

2.通讯录2.2:用Any字段接收下面的Address地址类型

contacts.proto

message Address
  {
    string home_addr = 1;
    string unit_addr = 2;
  }
    message People
  {
    string name = 1;
    int32 age = 2;
    //里面是电话的字段和类型
    message Phone
    {
        string num = 1;
        enum PhoneType 
        {
          MP = 0; // 移动电话
          TEL = 1; // 固定电话
        }
        PhoneType type = 2;
    }
    //repeated 表示重复  相当于定义一个数组 里面全是Phone
    repeated Phone phone = 3; 
    google.protobuf.Any data = 4;

write.cc(只展示新增部分)

contacts::Address address;
    std::string home_add;
    std::cout << "请输入联系人的家庭住址: ";
    getline(std::cin, home_add);
    address.set_home_addr(home_add);

    std::string unit_add;
    std::cout << "请输入联系人的单位住址: ";
    getline(std::cin, unit_add);
    address.set_unit_addr(unit_add);

    google::protobuf::Any *any = person->mutable_data();
    // address->Any
    any->PackFrom(address);

read.cc(只展示新增部分)

//has_data: 判断any对象是不是一个已经被赋值的数据   data():返回any对象,Is(): 模板函数,判断是否有这个类型
        if(person.has_data() && person.data().Is<contacts::Address>())
        {
            contacts::Address address;
            person.data().UnpackTo(&address);
            if(!address.home_addr().empty())
                std::cout << "联系人家庭住址: " << address.home_addr() << std::endl;
            if(!address.unit_addr().empty())
                std::cout << "联系人单位住址: " << address.unit_addr() << std::endl;
        }


http://www.kler.cn/a/467995.html

相关文章:

  • 什么样的人适合从事FPGA开发的工作?
  • OneFlow的简单介绍
  • Timer、Ticker使用及其注意事项
  • shell脚本总结2
  • 打造三甲医院人工智能矩阵新引擎(二):医学影像大模型篇--“火眼金睛”TransUNet
  • STM32的LED点亮教程:使用HAL库与Proteus仿真
  • Git关联多个仓库
  • HALCON中用于分类的高斯混合模型create_class_gmm
  • uniapp--HBuilder开发
  • 一些计算机零碎知识随写(25年1月)
  • YOLO系列的学习
  • Python中的OS库
  • 写一个类模板三个模板参数K,V,M,参数是函数(函数参数、lambda传参、函数指针)
  • 【CSS】 ---- CSS 实现图片背景清除的滑动效果三种方法
  • 2025年全面的AI学习计划
  • HTML——69.表单验证属性
  • 游戏引擎学习第71天
  • 周末总结(2024/01/04)
  • C语言:cJSON将struct结构体与JSON互相转换
  • 【音频伴奏分离】UVR5软件介绍
  • 安卓Activity执行finish后onNewIntent也执行了
  • CSS3——3. 书写格式二
  • Linux驱动开发(18):linux驱动并发与竞态
  • Mono里运行C#脚本22—mono_init_internal
  • 在DJI无人机上运行VINS-FUISON(PSDK 转 ROS)
  • leetcode-------mysql