Вопрос № 147893: Здравствуйте уважаемые эксперты! У меня такой вопрос: Дана целочисленная прямоугольная матрица A. Составить новую матрицу B из тех строк матрицы А, которые не содержат ни одного нулевого элемента. Данную задачу нужно решить двумя способами: с...
Вопрос № 147.893
Здравствуйте уважаемые эксперты! У меня такой вопрос: Дана целочисленная прямоугольная матрица A. Составить новую матрицу B из тех строк матрицы А, которые не содержат ни одного нулевого элемента. Данную задачу нужно решить двумя способами: с помощью статического и с помощью динамического массива. Помогите пожалуйста разобраться с данной задачей.
Отправлен: 20.10.2008, 19:23
Вопрос задал: Andryuha (статус: Посетитель)
Всего ответов: 3 Мини-форум вопроса >>> (сообщений: 7)
Отвечает: Verena
Здравствуйте, Andryuha! Для этой задачи можно использовать функцию, которая принимала бы строку матрицы и сообщала, есть ли в ней нули. Эта функция будет выглядеть так:
Код:
bool HasZeros (int *a, int n) //Функция проверяет наличие нулей в строке матрицы (в одномерном массиве по сути) { for
(int i=0; i<n; i++) if (a[i]==0) return false; //Есди попался ноль - возвращаем false return true; //Если возврата не произошло - возвращаем true }
Вариант её использования со статическими массивами совсем элементарен:
Код:
int _tmain(int argc, _TCHAR* argv[]) //Вариант со статическими массивами { int a[10][10], b[10][10]; //Массивы int m, n, mb; //Размерности cout << "Vvedite m i n: "; //Ввод cin >> m; cin >> n; cout << "Vvedite elementi:
"; for (int i=0; i<m; i++) for (int j=0; j<n; j++) cin >> a[i][j]; mb = 0; //Число строк массива b for (int i=0; i<m; i++) { //Идем по строкам массива а if (HasZeros (a[i], n)) { //Если в строке нет нулей for (int j=0; j<n; j++) //Переписываем строку в массив b b[mb][j] = a[i][j]; mb++; //Наращиваем размерность } } cout << "Resultat:
"; //Выводим результат for (int i=0; i<mb; i++) { for (int j=0; j<n; j++) cout << b[i][j] << ' '; cout << '
'; } getch(); return 0; }
С динамическими массивами тоже всё просто. Вопрос только в том, сколько памяти выделять под b. Можно было бы выделять её по мере надобности, но тогда очень много времени тратилось бы на перевыделение (удаление и выделение новой, большей области). Можно было бы сначала посчитать число необходимых строк и потом, выделив память, переписать элементы в массив, но это требовало бы множественных проходов по массиву или пометки необходимых строк. Я поступила
проще: выделила память под указатели на столько же строк, как в исходном массиве, а уже память для данных выделяла по мере надобности.
Код:
int _tmain(int argc, _TCHAR* argv[]) //Вариант с динамическими массивами { int **a, **b; //Массивы
int m, n, mb; //размерности cout << "Vvedite m i n: "; //Получаем размерность cin >> m; cin >> n; a = new int* [m]; //Выделяем память под указатели на строки b = new int* [m]; //От лишних указателей потеря памяти невелика, зато не будем тратить время на перевыделение или подсчёт cout << "Vvedite elementi:
"; //Ввод данных for (int i=0; i<m; i++) { a[i] = new int [n]; //Выделение памяти под сами строки for (int j=0; j<n; j++) cin >> a[i][j]; } mb = 0; //Размерность массива b for (int i=0; i<m; i++) { //Идём по строкам а if (HasZeros (a[i], n)) { //Если нет нулей b[mb] = new int [n]; //Выделяем память под саму строку for (int j=0; j<n; j++) //переписываем строку b[mb][j] = a[i][j]; mb++; //Наращиваем размерность } } cout
<< "Resultat:
"; //Вывод результата for (int i=0; i<mb; i++) { for (int j=0; j<n; j++) cout << b[i][j] << ' '; cout << '
'; } for (int i=0; i<mb; i++) //Очищаем память из-под реальных строк (их mb) delete [] b[i]; for (int i=0; i<m; i++) //Очищаем память из-под строк delete [] a[i]; delete [] a; //Очищаем память из-под указателей delete [] b; getch(); return 0; }
На всякий случай, полный код в приложении (одна функция main закомментирована). Удачи!
Приложение:
--------- Эта история - не для истории, понимаешь?
Ответ отправила: Verena (статус: Практикант)
Ответ отправлен: 20.10.2008, 20:28 Оценка за ответ: 5 Комментарий оценки: Огромное спасибо! Мне очень понравилось разьяснение, все коротко, понятно и очень быстро. Сейчас буду разбираться.
Отвечает: Navnav
Здравствуйте, Andryuha! Посылаю две отдельные программы для статического и динамического массивов. Сделаны в одном стиле, чтобы было легче разобраться. При поиске строки, содержащей ноль сначала предполагается, что строка не содержит ноль. Если в сроке появляется элемент, содержащий ноль, то поиск прекращается т.к. это бессмысленно (ноль уже есть). При работе с динамической памятью, для результирующей матрицы массив указателей выделяется с запасом, но это не страшно, т.к. указатель на любую строку
занимает 4 байта. Память для размещения элементов строки выделяется при необходимости.
Приложение:
Ответ отправил: Navnav (статус: 1-ый класс)
Ответ отправлен: 20.10.2008, 23:18 Оценка за ответ: 4 Комментарий оценки: Большое спасибо за помощь! Уже практически разобрался.
Отвечает: realbustard
Здравствуйте, Andryuha! Код в приложении. Раскоментируйте нужный метод и смотрите.
Приложение:
--------- Учись так, как-будто собираешься жить вечно; живи так, как-будто завтра умрешь (Отто фон Бисмарк)
Ответ отправил: realbustard (статус: 5-ый класс)
Ответ отправлен: 21.10.2008, 16:51 Оценка за ответ: 4 Комментарий оценки: Благодарю за помощь!