c – 具有标准布局结构的RVO,没有任何构造函数
我有一个代表二进制消息的结构.我想编写一个函数来从缓冲区获取下一个这样的记录(无论是文件还是套接字,都不重要):
template <typename Record> Record getNext(); 现在我可以这样写: template <typename Record> Record getNext() { Record r; populateNext(reinterpret_cast<char*>(&r),// maybe ::read() sizeof(r)); // or equivalent return r; } 这很好,给了我RVO的好处.但是,它将调用Record的默认构造函数,它可能由具有非希望默认构造函数的类型组成,这些构造函数可以避免使用 – 这些不一定是POD类型,但它们是标准布局. 有没有办法写入getNext(),以避免在Record上避免任何构造函数(默认或复制/移动)?理想情况下,当用户拨打: auto record = getNext<Record>(); 缓冲区直接读入记录的内存.这可能吗? 解决方法
no_init是一个no_init_t类型的常量.
如果从no_init_t构建一个pod,您将获得一个未初始化的pod,并且(假设elision)没有任何事情要做. 如果从no_init_t构造非pod,则必须覆盖构造函数,并使其不初始化数据.通常class_name(no_init_t):field1(no_init),field2(no_init){}将会这样做,有时class_name(no_init_t){}将会执行(假设所有内容都是pod). 然而,从每个成员的no_init构造可以作为一个健全检查,成员确实是pod.从no_init构造的非pod类将无法编译,直到您编写no_init_t构造函数. 这样(每个成员构造函数都不需要)确实会产生一些令人讨厌的DRY失败,但是我们没有反思,所以你会重复一遍,喜欢它. namespace { struct no_init_t { template<class T,class=std::enable_if_t<std::is_pod<T>{}>> operator T()const{ T tmp; return tmp; } static no_init_t instance() { return {}; } no_init_t(no_init_t const&) = default; private: no_init_t() = default; }; static const no_init = no_init_t::instance(); } struct Foo { char buff[1000]; size_t hash; Foo():Foo(""){} template<size_t N,class=std::enable_if_t< (N<=sizeof(buff)) >> Foo( char const(&in)[N] ) { // some "expensive" copy and hash } Foo(no_init_t) {} // no initialization! }; struct Record { int x; Foo foo; Record()=default; Record(no_init_t): x(no_init),foo(no_init) {} }; 现在我们可以用no_init构造Record,并且不会被初始化. 每个POD类都没有初始化.每个非POD类都必须提供一个no_init_t构造函数(可能最好实现非初始化). 然后你可以随便memcpy. 这需要修改您的类型及其包含的类型,以支持非初始化. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |
- (转)让quick-cocos2d-x支持加密的plist文件
- opencv 3 core组件进阶(3 离散傅里叶变换;输入输
- postgresql – Postgres为连接表的array_agg返回
- vb.net 教程 5-6图片上取色1
- 从Nand Flash启动U-BOOT的基本原理
- VUE中使用Vue-resource完成交互
- The database file is locked (database is lock
- ruby-on-rails-3 – 使用I18N从验证选项生成选择
- 10分钟掌握XML、JSON及其解析(中)
- c# – 实体框架4.1 RC:Code First EntityTypeCo