boost :: variant声称它是一个值类型.这是否意味着简单地写出boost :: variant的原始表示并稍后加载它是安全的,只要它只包含POD类型?假设它将由相同编译器编译的代码和相同版本的boost在同一架构上重新加载.
另外,(可能)等效地,可以在共享内存中使用boost :: variant吗?
我正在通过wxWidgets开发GUI应用程序.它有两部分:GUI部分和"逻辑"部分.我希望Logic部分完全独立于wxWidgets.但GUI中的一个组件返回wxVariant,我需要在逻辑部分使用它.
所以我正在寻找一种方法将wxVariant"转换"为boost :: variant
wxVariant的工作原理如下:
wxVariant v("37");
int i = v.GetInteger(); //i==37
Run Code Online (Sandbox Code Playgroud)
所以我在想类似的东西
string s = methodReturningWxVariant().GetString();
boost::variant bV(s);
//later in code e.g
bV.GetInt();
bV.GetBool();
Run Code Online (Sandbox Code Playgroud)
可以像这样使用boost :: Variant(或boost :: Any)吗?
如果我boost::variant支持的所有类型都使用相同的方法,那么有没有办法一般地调用它(即不为每个方法单独调用它static_visitor)?
我正试图让这样的东西起作用:
class A
{
void boo() {}
};
class B
{
void boo() {}
};
class C
{
void boo() {}
};
typedef boost::variant<A, B, C> X;
void foo(X& d)
{
x.boo();
}
Run Code Online (Sandbox Code Playgroud)
但它无法编译说'boo' : is not a member of 'boost::variant<T0_,T1,T2>'.
目前,我有一些类都继承自接口,因此可以多态地使用它们的单个共享方法.我还希望能够通过访问者使用这些类,因为所有其他方法对于每个具体类都是唯一的.我希望boost::variant可能是在这里实现我自己的访问者机制的更好的替代方案.是吗?
我正在见证以下代码中的一个我不理解的行为.关键是如果我声明第二个重载,operator()如下所示:
bool operator()(T other) const
bool operator()(const T &other) const
Run Code Online (Sandbox Code Playgroud)
程序的输出是:
串
但是,如果我使用以下声明:
bool operator()(T &other) const
Run Code Online (Sandbox Code Playgroud)
输出将是:
其他类型
有人可以解释为什么operator()(const string &other)在后一种情况下没有被调用?
#include "boost/variant/variant.hpp"
#include "boost/variant/apply_visitor.hpp"
using namespace std;
using namespace boost;
typedef variant<string, int> MyVariant;
class StartsWith
: public boost::static_visitor<bool>
{
public:
string mPrefix;
bool operator()(const string &other) const
{
cout << "string" << endl;
return other.compare(0, mPrefix.length(), mPrefix) == 0;
}
template<typename T>
bool operator()(T &other) const
{
cout << "other type" << endl; …Run Code Online (Sandbox Code Playgroud) 当应用多用户时,除了变量类型的参数之外,还有任何廉价的方法来传递非变量类型的参数吗?
我所说的"昂贵的方式"是指:
#include <boost/variant.hpp>
#include <iostream>
#include <cstdlib>
struct A {};
struct B {};
enum class C { X, Y };
std::ostream &
operator << (std::ostream & out, C const c)
{
switch (c) {
case C::X : {
return out << "C::X";
}
case C::Y : {
return out << "C::Y";
}
default : {
break;
}
}
throw std::runtime_error("unknown C value");
}
using V = boost::variant< A, B >;
struct S
: boost::static_visitor<>
{
void
operator () (C …Run Code Online (Sandbox Code Playgroud) 考虑变体类型和模板函数,如何检查模板类型是变体的类型之一?有比以下更优雅的方式吗?
typedef boost::variant<Foo,Bar> Var;
template <typename T>
void f(const T& x)
{
BOOST_STATIC_ASSERT(
boost::is_same<T,Foo>::value
|| boost::is_same<T,Bar>::value
);
}
Run Code Online (Sandbox Code Playgroud)
注意:我使用Boost 1.57和gcc 4.8.3.我不使用C++ 11与旧的gcc版本兼容.
我试图boost::variant使用不完整的包装类和std::vector我的间接技术来定义和访问"递归" .我的实现适用于libstdc ++,但不适用于libc ++.
这是我定义我的变体的方式:
struct my_variant_wrapper;
using my_variant_array = std::vector<my_variant_wrapper>; // <- indirection here
using my_variant = boost::variant<int, my_variant_array>;
struct my_variant_wrapper
{
my_variant _v;
template <typename... Ts>
my_variant_wrapper(Ts&&... xs) : _v(std::forward<Ts>(xs)...) { }
};
Run Code Online (Sandbox Code Playgroud)
我std::vector用来引入间接(因此动态分配将阻止my_variant具有无限大小).
由于纸张N4510 ("标准容器的最小不完全类型支持")std::vector<my_variant_wrapper>,我非常有信心我可以使用,哪里my_variant_wrapper是不完整的类型:
根据WG21的2015年页面,该论文获得批准.
根据此页面,libstdc ++始终支持这些功能.
根据这个页面,它在libc ++ 3.6中实现.
我随后访问该变体如下:
struct …Run Code Online (Sandbox Code Playgroud) 我有一个类似于此处描述的问题:C++相互递归变体类型
我试图在C++中创建一个JSON表示.许多库已经提供了非常快的优秀 JSON表示和解析器,但我并没有重新发明这个轮子.我需要创建一个C++ JSON表示,支持在特定条件下的某些空间优化.简而言之,当且仅当JSON数组包含同质数据,而不是将每个元素存储为膨胀变体类型时,我需要本机类型的紧凑存储.我还需要支持异构数组和标准嵌套JSON对象.
以下是"如果希望是马,乞丐会骑"版本的代码,这是为了清楚地说明意图,但显然是因为在任何声明存在之前使用类型而被破坏.我想避免在类型中多次指定相同的信息(即Array,Object和Value不应该需要重复的类型规范).我还想避免任何不必要的高运行时间成本.
#include <string>
#include <unordered_map>
#include <vector>
#include <boost/variant.hpp>
#include <boost/variant/variant.hpp>
#include <boost/variant/recursive_wrapper.hpp>
class JSONDocument {
public:
using String = std::string;
using Integer = long;
using Float = double;
using Boolean = bool;
using Null = void *;
using Key = std::string;
using Path = std::string;
using Value = boost::variant<
Null,
String,
Integer,
Float,
Boolean,
Object,
Array
>;
using Object = std::unordered_map<Key,Value>;
using Array = boost::variant<
std::vector<Null>,
std::vector<String>,
std::vector<Integer>,
std::vector<Float>,
std::vector<Boolean>,
std::vector<Value> >;
private: …Run Code Online (Sandbox Code Playgroud) 有没有办法让这项工作?我希望你能得到这个想法,我试图通过递归对创建一个列表
#include <boost/variant.hpp>
#include <utility>
struct nil {};
typedef boost::make_recursive_variant<nil, std::pair<int, boost::recursive_variant_ >>::type list_t;
int main() {
list_t list = { 1, (list_t){ 2, (list_t){ 3, nil() } } };
return 0;
}
Run Code Online (Sandbox Code Playgroud) 我的目标是保证所有变种类型的单一存储:根据Boost :: variant的'never empty'保证,我们需要覆盖
boost::has_nothrow_copy每个有界类型.但稍后文档提到了一些内容'boost::blank',如果该类型被绑定,variant将设置该值而不是尝试不提供默认的副本构造函数.
不清楚的是,如果在有界类型列表中添加boost :: blank将避免覆盖/专门化has_nothrow_copy
其他类型的要求吗?