10

The following piece of code does compile on gcc-4.7.1:

struct X {};

template <class T = X, typename U>
void f(const U& m) {
}


int main() {
    f<>(0);
}

However, this one doesn't:

struct X {};

template <class T = X, typename U>
void f(const U& m) {
    auto g = [] () {};
}


int main() {
    f<>(0);
}

gcc-4.7.1 complains:

c.cpp: In function 'void f(const U&)':
c.cpp:5:15: error: no default argument for 'U'

So my question is: is putting default parameters before non-default parameters correct in function template? If yes, why doesn't the second one compile? If no, why does the first one compile? How does C++11 standard say about this syntax?

5
  • stackoverflow.com/questions/2447458/… Commented Jul 27, 2012 at 9:25
  • @Andrew, the post you gave is too long. Can you point out which answer says about if it is correct to put default parameter before non-default ones? Commented Jul 27, 2012 at 9:31
  • 1
    @icando: There's nothing in the standard that forbids putting default template arguments for function templates anywhere. Only class templates are restricted. Commented Jul 27, 2012 at 9:43
  • 1
    @KerrekSB, so it is just a gcc bug that the code is not accepted? Commented Jul 27, 2012 at 9:47
  • @KerrekSB - I'd just arrived at the same conclusion. Interestingly clang3 .0 on my machine segfaults with the case that gcc rejects. Commented Jul 27, 2012 at 9:47

1 Answer 1

11

It is explicitly forbidden for classes and aliases. n3290 § 14.1.11 states:

If a template-parameter of a class template or alias template has a default template-argument, each subsequent template-parameter shall either have a default template-argument supplied or be a template parameter pack

For functions the only restriction seems to be related to parameter packs:

A template parameter pack of a function template shall not be followed by another template parameter unless that template parameter can be deduced or has a default argument

But clearly that doesn't concern this case.

Given that nothing in § 14 forbids it for functions it seems we have to assume it is permitted.

A note from a working group reports seems to confirm that this is the intention. The original proposed wording of that section is:

If a template-parameter of a class template has a default template-argument, all subsequent template-parameters shall have a default template-argument supplied. [Note: This is not a requirement for function templates because template arguments might be deduced (14.8.2 [temp.deduct]).]

I can't see where that note went in the final version though.

Sign up to request clarification or add additional context in comments.

2 Comments

I think it's allowed. If wasn't meant to be it's a defect in the standard that there is no wording rejecting it. clang on my system segfaults compiling it though too, so it's certainly problematic for compilers at the moment either way!
the clang-3.2 in my MacPorts actually compiles it. So maybe clang fixed that already?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.