Расширенный пакет параметров вариационного шаблона для вызовов функций
Я ищу что-то вроде этого:
template< typename T>
void func(T t)
{
}
template< typename... Parms>
void anyFunc( Parms... p)
{
func<Parms>(p)... ; //error
func(p)... ; //error
}
Если расширение пакета параметров выполняется внутри другого вызова функции, он работает:
template< typename T>
int some(T t)
{}
template< typename... Parms>
void func(Parms ...p)
{}
template< typename... Parms>
void somemore(Parms... p)
{
func( some(p)...);
}
int main()
{
somemore(1,2,3,4,10,8,7, "Hallo");
}
Расширение пакета параметров также будет работать для списка инициализаторов базового класса.
Есть ли какое-либо решение, которое также будет работать для функций, которые возвратят 'void'. Вышеописанное обходное решение не будет, в то время как использование вызовов функций, возвращающих void внутри списка параметров, никогда не будет работать.
Любые идеи?
Ответы
Ответ 1
К сожалению, как вы заметили, расширение пакета параметров действует только в определенных контекстах, где парсер ожидает список записей, разделенный запятыми, - контексты, в которых запятая является просто синтаксическим разделителем, а не оператором запятой. Это, возможно, недостаток в текущем тексте.
Уродливое обходное решение:
func((some(p), 0)...);
Обратите внимание, что порядок оценки аргументов функции и, следовательно, порядок вызовов some
не указан, поэтому вам нужно быть осторожным с любыми побочными эффектами.
Ответ 2
Как насчет небольшого вспомогательного класса:
template <typename Func, typename A, typename ...Args> struct Caller
{
static void call(Func & f, A && a, Args && ...args)
{
f(std::forward<A>(a));
Caller<Func, Args...>::call(f, args...);
}
};
template <typename Func, typename A> struct Caller<Func, A>
{
static void call(Func & f, A && a)
{
f(std::forward<A>(a));
}
};
template <typename Func, typename ...Args>
void Call(Func & f, Args && ...args)
{
Caller<Func, Args...>::call(f, std::forward<Args>(args)...);
}
Затем вы можете поместить в код клиента следующее:
void foo(A);
Call(foo, a1, a2, a3);