Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > C/C++ программирование > Общие вопросы C/C++
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 01.06.2011, 22:11   #1
Aistn
Пользователь
 
Регистрация: 01.06.2011
Сообщений: 10
По умолчанию указатели vs ссылки

Ребята есть две функции... та что через ссылки сделана работает та что через указатели нет... что я делаю не правильно?????

Код:
void result (float array[I][J], float &min, float &max, int &count) {
	max = min = array[0][0]; 
	count = 0;
	for (int i=0; i<I; i++) {
		for(int j=0; j<J; j++) {
			
			if (array[i][j] == 0) {
				count++;
			}
			if (min > array[i][j]) {
				min = array[i][j];
			}
			if (max < array[i][j]) {
				max = array[i][j];
			}	
		}
     }

void result (float **array, float *min, float *max, int *count) {
	*max = *min = array[0][0]; 
	*count = 0;
	for (int i=0; i<I; i++) {
		for(int j=0; j<J; j++) {
			
			if (array[i][j] == 0) {
				*count++;
			}
			if (*min > array[i][j]) {
				*min = array[i][j];
			}
			if (*max < array[i][j]) {
				*max = array[i][j];
			}	
		}
     }
при выполнении второй функции выскакивает в консоли ошибка сегментации а программа компилится... при этом из всех элементов работает нормально max указатель остальные нет
Aistn вне форума Ответить с цитированием
Старый 01.06.2011, 22:18   #2
Granus
С++
Форумчанин
 
Аватар для Granus
 
Регистрация: 22.09.2008
Сообщений: 791
По умолчанию

I,J объявлены глобально?

здесь вроде все правильно, покажите код создания массива и вызова самой функции
Форматируйте код, будьте людьми.
Granus вне форума Ответить с цитированием
Старый 01.06.2011, 22:28   #3
Aistn
Пользователь
 
Регистрация: 01.06.2011
Сообщений: 10
По умолчанию

Код:
#include <iostream>

#define I 5
#define J 6

using namespace std;

void outputArray(float**, char);
float **inputArray(char);
void result (float**, float*, float*, int*);

int main(int argc, char **argv) {
    float **a;
	float *min, *max;
	int *count;
	a = inputArray('A');
	outputArray(a, 'A');
	result(a, min, max, count);
	cout << "\nНаименьшее значение в массиве А: " << *min << endl;
	cout << "Наибольшее значение в массиве А: " << *max << endl;
    cout << "Количество нулевых значений в массиве А: " << *count << endl;
    return 0;
}

float **inputArray(char name) {
	float **p = new float *[I];
	cout << "Заполните массив: " << name << "["<< I << "][" << J <<"]"<< endl;
	for (int i = 0; i < I ;i++) {
		p[i] = new float [J];
		for(int j = 0; j < J ;j++) {
			cout << "Введите элемент " << name << "[" << i << "][" << j <<"] : ";
			cin >> p[i][j];
		}
	}
	return p;
}

// определение функции вывода массива на экран
void outputArray(float **array, char name) {
	int i,j;
	cout.setf( ios::showpoint | ios::fixed);
	cout << "\nМассив " << name ;
	for (i=0; i<I; i++) {
		cout << "\n";
		for(j=0; j<J; j++) {
			cout.width(8);     // минимальное кол-во позиций
			cout.precision(2);
			cout << array[i][j];
		}
     }

}

void result (float **array, float *min, float *max, int *count) {
	*max = *min = array[0][0]; 
	*count = 0;
	for (int i=0; i<I; i++) {
		for(int j=0; j<J; j++) {
			
			if (array[i][j] == 0) {
				*count++;
			}
			if (*min > array[i][j]) {
				*min = array[i][j];
			}
			if (*max < array[i][j]) {
				*max = array[i][j];
			}	
		}
     }
}
Aistn вне форума Ответить с цитированием
Старый 01.06.2011, 22:34   #4
Granus
С++
Форумчанин
 
Аватар для Granus
 
Регистрация: 22.09.2008
Сообщений: 791
По умолчанию

Код:
	float *min, *max;
	int *count;
	...
	result(a, min, max, count);
Вы создаете min, max и count как указатели. при создании они ни на что не указывают (в крайнем случае уж точно не на область памяти, Вашей программе выделенную).
Вам нужно либо передавать не указатели, а адреса переменных
Код:
	float min, max;
	int count;
	...
	result(a, &min, &max, &count);
	cout << "\nНаименьшее значение в массиве А: " << min << endl;
	cout << "Наибольшее значение в массиве А: " << max << endl;
	cout << "Количество нулевых значений в массиве А: " << count << endl;
...либо выделить память в указателях под переменные:
Код:
	float *min=new float, *max=new float;
	int *count=new int;
	...
	result(a, min, max, count);
	cout << "\nНаименьшее значение в массиве А: " << *min << endl;
	cout << "Наибольшее значение в массиве А: " << *max << endl;
	cout << "Количество нулевых значений в массиве А: " << *count << endl;
Форматируйте код, будьте людьми.

Последний раз редактировалось Granus; 01.06.2011 в 22:37.
Granus вне форума Ответить с цитированием
Старый 01.06.2011, 22:38   #5
Aistn
Пользователь
 
Регистрация: 01.06.2011
Сообщений: 10
По умолчанию

Спасибо большое)))) я просто недопонимал момента что под указатели нужно выделять память... я считал что при объявлении они резирвируют память как и обычные переменные))) спасибо))
Aistn вне форума Ответить с цитированием
Старый 01.06.2011, 22:42   #6
Granus
С++
Форумчанин
 
Аватар для Granus
 
Регистрация: 22.09.2008
Сообщений: 791
По умолчанию

При объявлении они как и обычные переменные просто создаются и в них записан какой-либо мусор. А так как указатель - это адрес в памяти, ни к чему хорошему это не приведет) Создавая что-то в памяти оператором new и записывая адрес созданного в указателем, мы обеспечиваем возможность работы с ним)

да, еще
если создаете в памяти оператором new, то потом обязательно удалите из памяти оператором delete

Код:
float *min=new float;
... // работа с указателем
delete min;
Форматируйте код, будьте людьми.
Granus вне форума Ответить с цитированием
Старый 01.06.2011, 22:48   #7
Aistn
Пользователь
 
Регистрация: 01.06.2011
Сообщений: 10
По умолчанию

буду иметь ввиду, спасибо...
То есть как я понял я не могу сделать так....
int *i;
*i=12;
???
Только
int *i;
i = new int;
*i =12;
??
Aistn вне форума Ответить с цитированием
Старый 01.06.2011, 22:50   #8
Granus
С++
Форумчанин
 
Аватар для Granus
 
Регистрация: 22.09.2008
Сообщений: 791
По умолчанию

Да, Вы абсолютно правы)
Компилятор это примет, но во время выполнения будет ошибка

кстати, так как вы таким же образом создаете массив
Код:
float **p = new float *[I];
...
то его тоже нужно бы удалить
Код:
for(i=0;i<I;++i)delete [] p[i];
delete [] p;
delete [] - оператор, удаляющий массив, адрес которого записан в указателе
Форматируйте код, будьте людьми.

Последний раз редактировалось Granus; 01.06.2011 в 22:53.
Granus вне форума Ответить с цитированием
Старый 01.06.2011, 22:54   #9
Aistn
Пользователь
 
Регистрация: 01.06.2011
Сообщений: 10
По умолчанию

Спасибо ещё раз за помощь)))
Aistn вне форума Ответить с цитированием
Старый 01.06.2011, 23:02   #10
Granus
С++
Форумчанин
 
Аватар для Granus
 
Регистрация: 22.09.2008
Сообщений: 791
По умолчанию

Получилось хорошее руководство по указателям :D
Форматируйте код, будьте людьми.
Granus вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
ссылки и указатели. mojohead Помощь студентам 13 14.01.2011 16:00
Найти и исправить ошибку. (Ссылки, указатели, утечка памяти) С,С++ ZanLeO Общие вопросы C/C++ 8 09.08.2010 13:00
C++ Указатели и ссылки - Вычислить площадь квадрата. Scarletred Помощь студентам 2 24.05.2010 03:49
C++ указатели. tshen Помощь студентам 3 16.04.2010 22:00
[C] массивы, указатели, двойные указатели. Iggel Общие вопросы C/C++ 5 05.05.2009 12:39