alf*_*lfC 10 c++ auto c++11 regular-type
更新:有人建议auto在某些情况下改变其含义.
Joel Falcou等人对"自动"变量和论证的隐含评价.
隐含评估应:
- 使类实现者能够指示在auto语句中评估此类的对象;
- 使它们能够确定评估对象的类型;
...
C++ 11的auto关键字很棒.
但是在我看来,如果一个类型是非常规的(参见例如,在移动语义的上下文中什么是"常规类型"?),则使用auto变得棘手.
有没有办法禁用auto这种类型的声明?
假设有一个ref模拟引用的类
double 5.;
ref<double> rd = d; // `ref` behaves like a reference, so it is not a regular type
ref<double> rd2 = rd; // `ref` can be (syntactically) copy constructible, (it is not regular for other reason)
auto r = rd; // now r is not `double`, but EVEN WORST it is `ref<double>`.
Run Code Online (Sandbox Code Playgroud)
(在现实生活中,这将是一个更复杂的课程,重要的一点是,手头的课程不规律.)
我发现auto r = rd不工作的唯一方法(给出编译错误)是使类不可复制,但是我需要类具有复制构造函数(具有特殊语义,但仍然是复制构造函数).
有没有办法以auto r = rd某种方式禁用语法?什么时候decltype(rd)不规律.
(更好的方法是能够以某种方式告诉编译器auto应该做什么).
注意:这不是一个非常人为的问题,可以看出这类问题是核心问题std::vector<bool>::reference(也是一个参考包装器).禁用(某种程度上)语法auto b = v[10]不会解决问题,std::vector<bool>但会使得糟糕的使用更加困难.
我错过了什么吗?我应该改变设计的其他部分吗?如果非普通班有一种特质,这将有助于编译器确定一个更一般的汽车(例如演绎bool的auto b = v[10]地方std::vector<bool> v.)
复制构造函数意味着您希望复制该类。auto x = y;复制y到x.
如果您想要一个超级特殊的副本,并且不想自动运行,则可以使用代理对象。
template <class T>
struct pseudo_copy;
template <class T>
struct pseudo_copy<T const&> {
T const& t;
// T const& can be initialized from T&&:
pseudo_copy(T const& tin) :t(tin) {}
pseudo_copy(T&& tin): t(tin) {}
pseudo_copy(pseudo_copy const&) = delete;
};
template <class T>
struct pseudo_copy<T&&> {
T&& t;
pseudo_copy(T&& tin): t(std::move(tin)) {}
pseudo_copy(pseudo_copy const&) = delete;
};
template <class T>
pseudo_copy<T const&> pseudo(T& t) { return {t}; }
template <class T>
pseudo_copy<T&&> pseudo(T&& t) { return {t}; }
struct strange {
strange(strange const&)=delete;
strange(pseudo_copy<strange const&>) {} // copy ctor
strange(pseudo_copy<strange&&>) {} // move ctor
strange() = default;
};
Run Code Online (Sandbox Code Playgroud)
现在我们可以:
strange foo() { return pseudo(strange{}); }
strange x = pseudo(foo());
Run Code Online (Sandbox Code Playgroud)
现在,每次尝试复制strange 都必须调用pseudo,并且使用auto永远不合法,因为没有任何东西具有复制构造函数。
您还可以将复制构造函数设为私有,并使用它来实现pseudo复制构造函数。
请注意,复制/移动向量的含义受到 C++ 中省略规则的限制。
在 C++17 模板类类型推导中可以得出:
template <class T>
struct value{
value_type_of<T> v;
value(T in): v(std::forward<T>(in)) {}
};
int x = 3;
value a = std::ref( x );
Run Code Online (Sandbox Code Playgroud)
并且a.v将是一个int.
| 归档时间: |
|
| 查看次数: |
364 次 |
| 最近记录: |