【问题标题】:Can placeholder type in non-type template parameter involve overload resolution of the function passed as a template argument?非类型模板参数中的占位符类型可以涉及作为模板参数传递的函数的重载解析吗?
【发布时间】:2018-01-28 10:43:05
【问题描述】:

this question 的跟进。假设占位符可用于推断构成非类型模板参数的函数指针的结果类型。 c++17 是否允许在传递给模板函数名称时执行重载解析 - 在不知道结果类型的情况下,执行隐式转换需要这样做吗?

template <auto(*)(int)>
struct Foo { };

int bar(int);
float bar(float);

int main() {
    static_cast<void>(Foo<bar>{});
}

[gcc][clang] 似乎接受了代码。

【问题讨论】:

  • @Rakete1111 不错!!我认为它涵盖了这个问题,谢谢!
  • @Rakete1111 我认为子弹在 c++14 中已经存在... :o 当时这个子弹的用途是什么?
  • 跟现在的用法一样。除非你从重载集中选择一个特定的函数,你自己为模板参数指定返回类型。

标签: c++ templates language-lawyer c++17


【解决方案1】:

是的,根据very bullet Rakete1111 pointed out 是允许的。而且也没有必要只假设它可以做到,它是按照[dcl.type.auto.deduct]/4的占位符类型推导规则完成的,强调我的:

如果占位符是自动类型说明符,则推导出的类型 T' 替换 T 是使用模板参数的规则确定的 扣除。通过将出现的 auto 替换为 T 从 T 中获取 P 要么是新发明的类型模板参数 U,要么,如果 初始化是复制列表初始化,其中 std​::​initializer_list。 使用以下规则推导出 U 的值 从函数调用中推导模板参数,其中 P 是 函数模板参数类型,对应的实参是e。 如果扣除失败,则声明格式错误。否则,T' 将推导出的U代入P中得到。

[temp.deduct.call]/6 有这一段,与您的用例有关:

当 P 是函数类型、函数指针类型或指向成员的指针时 函数类型:

  • 如果参数是包含一个或多个函数模板的重载集,则参数被视为非推导上下文。

  • 如果参数是重载集(不包含函数模板),则尝试使用每个 集合的成员。 如果只有其中一项扣减成功 重载集成员,该成员用作参数值 扣减。如果扣减成功的多于一名成员 重载设置参数被视为非推导上下文。

所以你拥有它的所有荣耀。

【讨论】:

  • 我错过的是你最后引用的一段:)
  • 太棒了!可惜 gcc 在其自动模板参数的实现中有一个讨厌的错误,因为它会成为一个非常强大的机制......谢谢!!!
猜你喜欢
  • 2019-04-24
  • 2018-02-28
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-09-23
  • 2011-07-06
  • 2012-10-25
  • 1970-01-01
相关资源
最近更新 更多