Как написать функцию с неопределенным количеством аргументов на C++?
Задание:
Написать функцию sum с переменным числом параметров, которая находит сумму чисел типа int по формуле:
S=a1*a2+a2*a3+a3*a4+. . . . .
Написать вызывающую функцию main, которая обращается к функции sum не менее трех раз с количеством параметров 5, 10, 12
Не могу понять как вообще это cstdarg работает. Как я понимаю все это дело какой древний рудимент C? Какие есть альтернативы для решения задачи?
Ответы (2 шт):
Простейшее решение с stdarg:
int sum(int count, ...)
{
va_list ap;
va_start(ap,count);
int Sum = 0;
int a = va_arg(ap,int);
for(int i = 1; i < count; ++i)
{
int b = va_arg(ap,int);
Sum += a*b;
a = b;
}
va_end(ap);
return Sum;
}
int main(int argc, char * argv[])
{
cout << sum(5,1,2,3,4,5) << endl;
}
С шаблонами набросал на коленке (т.е. не то, что допускаю — уверен, что может быть более красивый вариант) так:
int SumAux(int a0, int S, int x)
{
return S + a0*x;
}
template<typename... Args>
auto SumAux(int a0, int S, int x, Args... args)
{
S += a0 * x;
return SumAux(x, S, args...);
}
template<typename... Args>
auto Sum(int x, int y, Args... args)
{
return SumAux(x,0,y,args...);
}
int main(int argc, char * argv[])
{
cout << Sum(1,2,3,4,5) << endl;
}
Чуть покороче — две SumAux заменяются одной:
template<typename... Args>
auto SumAux(int a0, int S, int x, Args... args)
{
S += a0 * x;
if constexpr (sizeof...(args) == 0) return S;
else return SumAux(x, S, args...);
}
В случае одинаковых типов аргументов шаблона можно для простоты превращать их в какой-нибудь вектор:
#include <iostream>
#include <vector>
template <class... Args>
int sum(const Args&... args) {
std::vector<int> a{static_cast<int>(args)...};
const int count = a.size()-1;
int out = 0;
for (int i = 0; i < count; i++) {
out+=a[i]*a[i+1];
}
return out;
}
int main()
{
std::cout << sum(1,2,3,4,5) << std::endl;
std::cout << sum(1,2,3.2,4,5) << std::endl;
return 0;
}