I am writing a template function where one of the template parameters is a type with a member function that is itself a template function. When I invoke the template member function and explicitly specify the template parameters, it appears that the code does not compile. This is illustrated in the following minimal example:
This version will compile and run just fine:
#include <iostream>
struct ar_t
{
int data[2];
ar_t(void) {data[0] = 10; data[1] = 17;}
template <const std::size_t idx> int get(void) const {return data[idx];}
};
template <const std::size_t val> struct idx_t {};
template <const std::size_t val> int idx_ar1(const ar_t& ar, const idx_t<val>& idx)
{
return ar.get<val>();
}
int main(int argc, char** argv)
{
ar_t x;
const std::size_t index = 1;
idx_t<index> i;
idx_ar1(x,i);
return 0;
}
whereas this version will not:
#include <iostream>
struct ar_t
{
int data[2];
ar_t(void) {data[0] = 10; data[1] = 17;}
template <const std::size_t idx> int get(void) const {return data[idx];}
};
template <const std::size_t val> struct idx_t {};
template <typename arr_type, const std::size_t val> int idx_ar1(const arr_type& ar, const idx_t<val>& idx)
{
return ar.get<val>();
}
int main(int argc, char** argv)
{
ar_t x;
const std::size_t index = 1;
idx_t<index> i;
idx_ar1(x,i);
return 0;
}
Note the difference in the template parameters for idx_ar1
. The error message I get with g++ 11.1 and -std=c++20
is:
main.cc: In function ‘int idx_ar1(const arr_type&, const idx_t<val>&)’:
main.cc:14:24: error: expected primary-expression before ‘)’ token
14 | return ar.get<val>();
| ^
main.cc: In instantiation of ‘int idx_ar1(const arr_type&, const idx_t<val>&) [with arr_type = ar_t; long unsigned int val = 1]’:
main.cc:22:12: required from here
main.cc:14:18: error: invalid operands of types ‘<unresolved overloaded function type>’ and ‘long unsigned int’ to binary ‘operator<’
14 | return ar.get<val>();
|
How can I get around this? I require preciesly the behaviour used in the second example. This appears to be a bug in parsing the syntax, or I don't quite have a detailed understanding of the way the member function is being declared.