Template template parameter and default values [duplicate]

强颜欢笑 提交于 2019-11-26 18:34:26

问题


This question already has an answer here:

  • Deducing first template argument with other template parameters defaulted 2 answers

Consider the following code:

template<typename T>
struct A { };

// same as A, but with one extra defaulted parameter
template<typename T, typename F = int>
struct B { };

template<template<typename> typename T>
T<int> build() { return {}; }

int main()
{
    build<A>();  // works in gcc and clang
    build<B>();  // works in gcc, does not work in clang
}

g++ (7.3.0) compiles the code just fine, however, clang++ (5.0.1) emits the following:

example.cpp:14:5: error: no matching function for call to 'build'
    build<B>();  // works in gcc, does not work in clang
    ^~~~~~~~
example.cpp:9:8: note: candidate template ignored: invalid
      explicitly-specified argument for template parameter 'T'
T<int> build() { return {}; }

Which of the compilers is right?


Note: The important line is obviously:

template<template<typename> typename T>

Because both compilers are satisfied with:

template<template<typename...> typename T>

So the question is whether default values should be considered when passing template template arguments.


回答1:


As far I know, your code is correct starting from C++17, wrong before.

This according P0522R0, that is part of new standard, where I see an example that is very, very similar to your code (see "overview"):

template <template <typename> class> void FD();
template <typename, typename = int> struct SD { /* ... */ };
FD<SD>();  // OK; error before this paper (CWG 150)

According the compiler support tables in ccpreference, g++ support P0522R0 from version 7, clang++ from version 4. So both compiler should support your code.

But looking the table in this page, the support for llvm (clang) 5 is defined "partial" and, according a note,

(12): Despite being the the resolution to a Defect Report, this feature is disabled by default in all language versions, and can be enabled explicitly with the flag -frelaxed-template-template-args in Clang 4 onwards. The change to the standard lacks a corresponding change for template partial ordering, resulting in ambiguity errors for reasonable and previously-valid code. This issue is expected to be rectified soon.

So, at your risk, you can try with the flag -frelaxed-template-template-args.



来源:https://stackoverflow.com/questions/48645226/template-template-parameter-and-default-values

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!