Использование аргументов по умолчанию для std :: index_sequence

У меня есть трудности, чтобы понять следующее. Почему этот код компилируется

template <size_t N, size_t... N_i, size_t... M_i>
auto foo2(std::index_sequence<M_i...> = std::make_index_sequence<N>())
{

constexpr size_t values[] = {N_i...};
return A<values[M_i]...>();
}template <size_t N,size_t... N_i>
auto foo()
{
return foo2<N,N_i...>(std::make_index_sequence<N>());
}int main()
{
foo<2, 1,2,3>();
}

но это не так (где я использую аргумент по умолчанию foo2):

template <size_t N, size_t... N_i, size_t... M_i>
auto foo2(std::index_sequence<M_i...> = std::make_index_sequence<N>())
{

constexpr size_t values[] = {N_i...};
return A<values[M_i]...>();
}template <size_t N,size_t... N_i>
auto foo()
{
return foo2<N,N_i...>();
}int main()
{
foo<2, 1,2,3>();
}

Спасибо заранее.

3

Решение

Дано:

template <size_t N, size_t... N_i, size_t... M_i>
auto foo2(std::index_sequence<M_i...> = std::make_index_sequence<N>());

Вы не можете явно указать M_i (потому что последовательность будет просто поглощена как часть N_i). Если вы укажете аргумент, то компилятор может использовать вывод аргумента шаблона, чтобы выяснить, что M_i является. если ты не указать аргумент, то компилятор не может сделать вывод, что M_i есть (и он должен знать, что прежде чем он сможет начать принимать решение, вам нужен аргумент по умолчанию и что это за аргумент).

Если предположить, что это меньшая часть большего целого, тогда нужно исправить

template <size_t N, size_t... N_i, size_t... M_i>
auto foo2(std::index_sequence<M_i...>)
{

constexpr size_t values[] = {N_i...};
return A<values[M_i]...>();
}template <size_t N,size_t... N_i>
auto foo2()
{
return foo2<N,N_i...>(std::make_index_sequence<N>());
}

Тогда вы действительно можете написать:

template <size_t N,size_t... N_i>
auto foo()
{
return foo2<N,N_i...>();
}
4

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]