从替代方案构建的变体中返回构造
return a constructible from a variant being constructed from an alternative
可以拥有一个可以从变体中构造的结构(例如,从std :: variant)构造,并且要返回从变体的替代方案之一中隐含构建的这种结构?p>考虑以下代码:
#include <utility>
struct type1_t
{
};
struct type2_t
{
};
struct variant
{
/*template <typename T>
variant(T&& t)
{}*/
variant(type1_t){}
};
struct var_holder_t
{
var_holder_t(variant v)
: m_var(std::move(v))
{}
private:
variant m_var;
};
var_holder_t foo()
{
return type1_t{ }; // <====== offending line
}
MSVC 2017,2019允许这样做,但GCC和Clang并未编译。更改为另一个变体的构造函数,甚至使用boost ::变体或std ::变体无济于事。
值得注意的是,将有问题的线更改为return {type1_t{ }};
使其以某种方式编译。目前,我迷路了,尽管从技术上讲,添加两个额外的{}并没有造成太大的伤害可读性,但现在我会坚持这一点,只是希望答案。
还可以使var_holder_t的构造函数模板(转发)有助于它可以直接从type1_t构造的var_holder_t(在性能方面非常好),但是目前我想保留var_holder_t完全非template-思想,设计)是随便写的简单代码。
更新:实际上让我感到困惑的是,Clang发出了此消息:
note: candidate constructor not viable: no known conversion from 'type1_t' to 'variant' for 1st argument var_holder_t(variant v)
这很奇怪,因为显然有从type1_t
转换为variant
,但看起来只是伪造的诊断。将其汇总在一起,我认为我可以提出一个简单的原因,使上面的构建不起作用:它需要两个隐式转换,但是规则仅考虑一个。
以下语句有效,因为正在执行列表初始化。
return {type1_t{ }};
复制列表initialization
return { arg1, arg2, ... } ; (8)
列表初始化在以下情况下执行:
...
直接列表初始化(考虑了明确和不明显的构造函数)
...
8)在带有支撑列表的返回语句中,用作返回表达式, list-Initialization初始化返回的对象
此处用type1_t
对象初始化var_holder_t
,并且可以按预期工作。
- 来自 std::list 的迭代器 .end() 按预期返回"0xcdcdcdcdcdcdcdcd"但 .begin()
- 运行同一解决方案的另一个项目的项目
- 什么时候在C++中返回常量引用是个好主意
- 你能重载对象变量名本身返回的内容吗
- 为什么 Serial.println(<char[]>);返回随机字符?
- C++映射:具有自定义类的运算符[]不起作用(总是返回0)
- 如何获取std::result_of函数的返回类型
- QueryWorkingSet总是返回false
- (C++)分析树以计算返回错误值的简单算术表达式
- 访问者访问变体并返回不同类型时出错
- Project Euler问题4的错误解决方案
- 我可以在C++中返回跨度吗?如果是这样,如何?(对替代方案开放
- 从替代方案构建的变体中返回构造
- 使用霍尔分区方案的快速排序算法返回原始未排序列表
- std::optional 的最佳替代方案是从方法返回可选值?(使用 C++98/C++11/C++14)
- 采用N个参数并返回N个值的高性能解决方案
- 返回值复制问题(以改进调试时间)-- 这里的解决方案是什么?
- 调用返回类型不完整的方法和无法解释的模板解决方案
- 创建并返回字符串向量——最有效的解决方案
- C++中返回局部变量的引用和标准指针的替代方案是什么