当前位置:  开发笔记 > 编程语言 > 正文

可变版本的std :: is_convertible?

如何解决《可变版本的std::is_convertible?》经验,为你挑选了2个好方法。

是否可以编写可变版本的std::is_convertible?例如are_convertible会返回is_convertible && is_convertible.我一直在考虑这个问题几个小时但是无法提出任何合理的建议.

澄清我想使用它有点像这样:

template 
struct thing
{
  template 
  enable_if_t::value>
  foo(Args2 &&...args){}
}

小智.. 12

你并不需要连接Args2...Args1...,你不应该,因为这样做,以使得它使得它不可能知道Args2...结束和Args1...开始.以允许单独提取它们的方式传递多个可变参数的方法是将它们包装在另一个模板中:给定一个可变参数模板my_list,您可以将您的结构my_convertible称为

my_convertible, my_list>

标准库已经有一个可变的模板,在这里运行良好:tuple.不仅如此,而且tuple可转换为tupleif且仅当Args2...可转换为Args1...,所以你可以写:

std::is_convertible, std::tuple>

注意:在评论中,@ zatm8报告这并不总是有效:std::is_convertible, std::tuple>::value报告为false,但std::is_convertible::value报告为true.

我相信这是一个错误,它们都应该被报告为true.这个问题可以在http://gcc.godbolt.org/和clang 3.9.1 上重现.它不能用gcc 6.3重复,并且在使用时也不能用clang 3.9.1重现-stdlib=libc++.似乎libstdc ++正在使用clang不能正确处理的语言功能,并将其简化为一个不依赖于标准库头的简短示例,它给出了:

struct S {
  S(const char *) { }
};
int main() {
  const char *s = "";
  static_cast(s);
}

这被gcc接受,但被clang拒绝.它在2014年报告为https://llvm.org/bugs/show_bug.cgi?id=19917.

看起来这已经在2016年底修复,但修复程序还没有发布到发布版本:http://lists.llvm.org/pipermail/cfe-commits/Week-of-Mon-20161031/175955. HTML

如果您受此影响,您可能希望避免std::tuple使用@Yakk的答案.



1> 小智..:

你并不需要连接Args2...Args1...,你不应该,因为这样做,以使得它使得它不可能知道Args2...结束和Args1...开始.以允许单独提取它们的方式传递多个可变参数的方法是将它们包装在另一个模板中:给定一个可变参数模板my_list,您可以将您的结构my_convertible称为

my_convertible, my_list>

标准库已经有一个可变的模板,在这里运行良好:tuple.不仅如此,而且tuple可转换为tupleif且仅当Args2...可转换为Args1...,所以你可以写:

std::is_convertible, std::tuple>

注意:在评论中,@ zatm8报告这并不总是有效:std::is_convertible, std::tuple>::value报告为false,但std::is_convertible::value报告为true.

我相信这是一个错误,它们都应该被报告为true.这个问题可以在http://gcc.godbolt.org/和clang 3.9.1 上重现.它不能用gcc 6.3重复,并且在使用时也不能用clang 3.9.1重现-stdlib=libc++.似乎libstdc ++正在使用clang不能正确处理的语言功能,并将其简化为一个不依赖于标准库头的简短示例,它给出了:

struct S {
  S(const char *) { }
};
int main() {
  const char *s = "";
  static_cast(s);
}

这被gcc接受,但被clang拒绝.它在2014年报告为https://llvm.org/bugs/show_bug.cgi?id=19917.

看起来这已经在2016年底修复,但修复程序还没有发布到发布版本:http://lists.llvm.org/pipermail/cfe-commits/Week-of-Mon-20161031/175955. HTML

如果您受此影响,您可能希望避免std::tuple使用@Yakk的答案.



2> Yakk - Adam ..:

是.

首先,如何做到这一点.那么,为什么你不应该这样做.

怎么做:

写重组,它取一个kN元素列表并将其分组为N组k,交错.团体可以templatestruct types{};.

然后编写apply,它接受一个templateclass Z和一个class...组(又名types<...>),并应用于Z每个包的内容,返回types<...>结果的一个.

然后折叠types<...>使用的内容template struct and_types:std::integral_constant{};.

我会发现这大多没有意义,所以我不会实现它.使用一个像样的元编程库应该很容易,上面的大多数操作都是沼泽标准的.


为什么你不应该

但实际上,举个例子,就这样做:

template
struct and_types:std::true_type{};
template
struct and_types:std::integral_constant{}>{};

然后:

std::enable_if_t...>{}>

做的工作.所有的洗牌都只是噪音.

通过...C++ 1z的折叠支持,我们也可以摆脱and_types使用&&....

推荐阅读
地之南_816
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有