std :: add_pointer,在可能的实现中try_add_pointer的作用是什么? [英] std:: add_pointer, what the try_add_pointer for in the possible implementation?

查看:119
本文介绍了std :: add_pointer,在可能的实现中try_add_pointer的作用是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在cppreference add_pointer 中,我们可以将其实现为:

In cppreference add_pointer, it is said we may implement it as:

namespace detail {

template <class T>
struct type_identity { using type = T; }; // or use std::type_identity (since C++20)

template <class T>
auto try_add_pointer(int) -> type_identity<typename std::remove_reference<T>::type*>;
template <class T>
auto try_add_pointer(...) -> type_identity<T>;

} // namespace detail

template <class T>
struct add_pointer : decltype(detail::try_add_pointer<T>(0)) {};

我的问题是 try_add_pointer 是干什么的?我知道是SFINAE.但是为什么这里需要实现呢?

My question is what is the try_add_pointer for? I know it is SFINAE. But why the implementation need it here?

推荐答案

如果您阅读了有关cppreference的页面,您会注意到这句话

If you read over the page on cppreference, you'll notice this sentence

否则(如果T是cv或ref限定的函数类型),则提供成员typedef类型,即类型T.

Otherwise (if T is a cv- or ref-qualified function type), provides the member typedef type which is the type T.

函数有自己的类型.通常,您会在正常代码中看到的是类似 int(int)的类型,即,采用单个整数并返回整数的函数的类型.这是参数 std :: function 所期望的类型,例如 std :: function< int(int)> .

Function have their own types. Normally, what you'll see in sane code is types like int(int), i.e. the type of a function taking a single integer and returning an integer. This is the type of argument std::function expects, e.g std::function<int(int)>.

但是,函数类型集还包含与成员函数有关的奇数.例如

However the set of function types also contains oddities that relate to member functions. For instance

struct foo {
  int bar(int) const;
};

int(int)const bar 的函数类型.尽管此类型存在于类型系统中,但其用途受到限制.

int(int) const is the function type of bar. While this type exists in the type system, it is limited in its uses.

[dcl.fct]

6 一个cv-qualifier-seq或ref-qualifier只能是以下内容的一部分:

6 A cv-qualifier-seq or a ref-qualifier shall only be part of:

  • 非静态成员函数的函数类型,
  • 指向成员的指针所指向的函数类型,
  • 函数typedef声明或别名声明的顶级函数类型,
  • 类型参数([temp.param])的默认参数中的type-id,或者
  • 类型参数([temp.names])的模板参数的type-id.

在函数声明器中cv-qualifier-seq的作用不是与在函数类型的顶部添加cv-qualification相同.在里面在后一种情况下,将忽略cv限定词.[注意:函数类型具有cv-qualifier-seq的不是cv-qualified类型;没有具有cv资格的函数类型.—尾注] [示例:

The effect of a cv-qualifier-seq in a function declarator is not the same as adding cv-qualification on top of the function type. In the latter case, the cv-qualifiers are ignored. [ Note: a function type that has a cv-qualifier-seq is not a cv-qualified type; there are no cv-qualified function types. — end note ] [ Example:

typedef void F();
struct S {
  const F f;        // OK: equivalent to: void f();
};

—结束示例]返回类型,参数类型列表,ref-qualifier和cv-qualifier-seq,但不是默认参数([dcl.fct.default])或例外说明([except.spec]),是函数类型的一部分.

— end example ] The return type, the parameter-type-list, the ref-qualifier, and the cv-qualifier-seq, but not the default arguments ([dcl.fct.default]) or the exception specification ([except.spec]), are part of the function type.

因此trait允许您将其提供给 int()const 之类的函数类型,并且期望将其返回不变.

So the trait allows you to feed it a function type like int() const, and it's expected to return it unchanged.

那里是 try_add_pointer 的来源.由于从上面的列表中可以看到,没有常规的指针指向这些类型的函数,因此我们将在 typename std中得到替换失败::remove_reference< T> :: type * .但多亏SFINAE,回退存在.

That's where try_add_pointer comes in. Since as you can see from the list above, there are no regular pointers to these sort of functions, we will get a substitution failure in typename std::remove_reference<T>::type*. But thanks to SFINAE, a fallback exists.

这篇关于std :: add_pointer,在可能的实现中try_add_pointer的作用是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆