Форум программистов, компьютерный форум CyberForum.ru

Функция с переменным количеством параметров-оъектов - C++

Войти
Регистрация
Восстановить пароль
Другие темы раздела
C++ Интервальный таймер http://www.cyberforum.ru/cpp-beginners/thread261983.html
Добрый вечер. Мне очень нужна помощь в решении задачи на С++. 1) Должен быть метод, реализующий _один_ шаг работы таймера. Возвращать должен текущее состояние выхода (0 если счетчик не равен нулю, 1 если равен), при достижении счетчиком значения 0 он должен перезапускаться. 2) Соответственно, должны быть методы для установки интервала (максимального значения счетчика), его сброса, остановки и...
C++ Создание GET или POST запроса Всем привет. Подскажите, как создать гет или пост запрос на сайт? Например, адрес сайта http://site.ru и нужно сделать запрос вида http://site.ru/index.php?get=текст_запроса . Не мог бы кто предоставить готовое решение или дать ссылку на объёмную статью, где очень подробно говорится о создании запросов к web-ресурсам? http://www.cyberforum.ru/cpp-beginners/thread261978.html
C++ Используя механизм перегрузки функции
На уроке преподаватель не объясняет как решать. Задачи берутся из "Основы программирования на языке С++" часть 2 Огнева М.В., Кудрина Е.В. Помогите, пожалуйста Разработать две версии функции F, заголовки которых выглядят след. образом: 1. float F (float x); 2. void F (float x, float &y); Систему: y= x, если x>0; =0, если -1<=x<=0; = x в квадрате, если x< -1.
Использование функций-шаблонов C++
На уроке преподаватель не объясняет как решать. Задачи берутся из "Основы программирования на языке С++" часть 2 Огнева М.В., Кудрина Е.В. Помогите, пожалуйста Для работы с двумерными массивами арифметических типов данных разработать шаблоны ввода и вывода массива, и также шаблон для решения основной задачи: -> Если количество строк в массиве четное, то поменять строки местами по правилу:...
C++ Распараллеливание потоков http://www.cyberforum.ru/cpp-beginners/thread261958.html
Добрый день. У меня есть программ в которой Пузырьковая сортировка и Бинарный поиск выполняются в отдельных потоках, причём изначально они приостановленные, а уже в main'е в определённых моментах я к ним обращаюсь с помощью ResumeThread(). Нужно решить две задачи на распараллеливание. Первая: Распараллелить пузырьковую сортировку и main, таким образом что бы на каждой итерации сортировки...
C++ определить принадлежность точки треугольнику определить принадлежит ли точка, заданная координатам, треугольнику, который задан координатами вершин. КАК задать треугольник? и как потом определить принадлежит (не принадлежит) точка которую мы задаем для нашего треугольника? визначити чи належить точкаБзадана координатам,трикутнику,який заданий координатами вершин.ЯК задати трикутник? і як потім визначити чи належить(не належить) точка яку... подробнее

Показать сообщение отдельно
Kastaneda
Форумчанин
Эксперт С++
4652 / 2860 / 228
Регистрация: 12.12.2009
Сообщений: 7,268
Записей в блоге: 2
Завершенные тесты: 1
22.03.2011, 19:56
Должно помочь
Постоянная работа с функциями типа printf или scanf вызывает у программистов зависть – это же функции с переменным количеством аргументов. А как написать свою функцию, обрабатывающую столько параметров, сколько будет задано в обращении, и, естественно, допускающую задание разного количество аргументов?

Рассмотрим в качестве примера функцию, вычисляющую среднее арифметическое нескольких своих аргументов, имеющих тип double. Вызванная функция может догадаться о количестве переданных ей параметров только в том случае, если ей сообщают (например, значением первого аргумента) это число n, либо список параметров завершается обусловленным признаком – например, нулевым значением последнего параметра.

Если мы собираемся сообщать функции количество передаваемых ей аргументов, то заголовок функции можно оформить следующим образом:
double mid_var(int n,...)

Три точки в конце списка предупреждают компилятор о том, что он не должен контролировать количество и типы следующих аргументов. Все заботы о доступе к списку параметров переменной длины берет на себя вызываемая функция. Предположим, далее, что все аргументы передаются в функцию mid_var как значения, т.е. к моменту передачи управления функции они находятся в стеке. Добраться до них можно следующим образом. Заведем указатель типа int и занесем в него адрес формального параметра n (система знает, где находится стек, и адрес n ей доступен):
int *ip=&n;

Продвинем указатель ip на 1, т.е. переместимся на адрес начала следующего параметра, и занесем его в новый указатель dp уже типа double:
ip++; //переход на адрес первого слагаемого
double *dp=(double *)ip; //преобразование типа указателя

Теперь адрес начала списка слагаемых у нас есть, количество слагаемых мы тоже знаем, поэтому все остальное – дело техники. Окончательный вид функции таков:
double mid_var(int n,...)
{ int *ip=&n+1;
double *dp=(double *)ip;
double s=0.;
for(int j=0; j<n; j++)
s += dp[j]; //или s += *(dp+j); или s += *(dp++);
return s/n;
}

Теперь попытаемся построить аналогичную функцию, которая суммирует свои аргументы до тех пор, пока не встречает нулевое слагаемое. Она устроена еще проще:
double mid_var(double a1,...)
{ double *dp=&a1;
double s=0;
int c=0;
while(*dp != 0)
{ s += *(dp++); c++; }
return s/c;
}

Аналогичные функции можно построить, когда список передаваемых параметров состоит из переменного количества однотипных указателей. Только здесь придется использовать не просто указатели типа *dp, а "двойные" указатели типа **dp. И доставать значения нужных данных придется также через двойные указатели s += (**dp);

В файле stdarg.h находится несколько функций (точнее, макроопределений) которые обеспечивают перемещение по списку параметров, завершающемуся нулем:
va_list p; //объявление указателя на список параметров
va_start(p,p1); //установка указателя списка на последний явный
//параметр
va_arg(p,тип); //перемещение указателя на очередной неявный параметр
va_end(p); //уничтожение указателя на список параметров

Продемонстрируем использование этих средств на примере той же самой функции mid_var:
double mid_var(int n,...) //функции передают количество параметров
{ va_list p;
double s=0,c=0;
va_start(p,n);
while(n--) //до тех пор, пока n != 0
{ s += va_arg(p,double); c++; }
va_end(p);
return s/c;
}

Если список параметров начинается с первого слагаемого a1, то программа меняется очень незначительно:
double mid_var(double a1,...)
{ va_list p;
double s=0,c=0,u=a1;
va_start(p,a1);
do {s += u; c++; }
while(u=va_arg(p,double)); //до тех пор, пока u != 0
va_end(p);
return s/c;
}

На наш взгляд, применение обычных указателей выглядит несколько проще, чем использование стандартных средств.
 
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Рейтинг@Mail.ru