Форум программистов, компьютерный форум, киберфорум
C++ Builder
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.64/25: Рейтинг темы: голосов - 25, средняя оценка - 4.64
Техник
 Аватар для DenProx
318 / 176 / 27
Регистрация: 09.10.2009
Сообщений: 3,109

Удаление двумерного массива

29.07.2015, 09:33. Показов 4817. Ответов 20
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Доброго времени суток! Подскажите пожалуйста, как правильно удалить двумерный массив, созданный таким образом:

C++
1
2
3
4
5
6
7
8
9
10
11
Graphics::TBitmap *Bitmap_elps[8][10];
//---------------
for (int i=0; i < 8; i++) {
for (int j=0; j < 10; j++) {
 
Bitmap_elps[i][j] = new Graphics::TBitmap;
 
//заполнение массива
 
}
}
на сколько я понимаю, просто

C++
1
delete Bitmap_elps;
не прокатит ?
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
29.07.2015, 09:33
Ответы с готовыми решениями:

Удаление двумерного динамического массива
Здравствуйте. Возникла ошибка при удалении двумерного динамического массива: сам код: TStringList** TMP_CAT = new...

Удаление одинаковых строк двумерного массива
Доброе время суток дамы и господа. сижу в С++ Builder'e 6, имеется массив чисел otvetibuff 110000...000 110000...000 ...

Удаление двумерного массива объектов без утечки памяти
Как удалить созданные объекты без утечки памяти? Screen = new TPanel**; for(int i = 0; i &lt; N; i++) { Screen = new...

20
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33405 / 21515 / 8236
Регистрация: 22.10.2011
Сообщений: 36,917
Записей в блоге: 12
29.07.2015, 10:00
Цитата Сообщение от DenProx Посмотреть сообщение
не прокатит ?
Разумеется, нет. Сам массив Bitmap_elps - статический, его нельзя удалять вообще. Освобождать надо таким же вложенным циклом, как и при создании элементов:
C++
1
2
    for(int i = 0; i < 8; i++)
      for (int j = 0; j < 10; j++) delete Bitmap_elps[i][j];
1
Техник
 Аватар для DenProx
318 / 176 / 27
Регистрация: 09.10.2009
Сообщений: 3,109
29.07.2015, 10:07  [ТС]
volvo, Спасибо! Помогло. Не думал что сами элементы массива удалять обязательно.
Предполагал, что нужно, что-то типа такого:
C++
1
2
for(int i = 0; i < 8; i++)
 delete Bitmap_elps[i];
0
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
29.07.2015, 11:11
..непонятная для меня вещь получается... - если этот двумерный массив объявлен как общая переменная и на кнопку заведен цикл удаления, предложенный volvo , то на кнопку давишь многократно - и всё ОК, никаких тебе ругательств. Но если только предварительно массив инициализировать ( = new Graphics::TBitmap; ), то кнопка удаления сработает первый раз; потом - сплошной фиолетовый аксэс... . Что поменялось после инициализации для вот этой вот Bitmap_elps[i][j] ?
0
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
29.07.2015, 12:47
- nick42, в циклы volvo надо ставить вот это:
C++
1
2
3
4
5
6
  for ( ... )
  for ( ... )
  {
    delete  Bitmap_elps[i][j];
    Bitmap_elps[i][j] = NULL;  //(!!!!!)
  }
, тогда все будет "OK".

Добавлено через 1 минуту
- А вообще-то лучше, наверно, блокировать Button, чтобы не удаляла то, чего нет!
0
Супер-модератор
Эксперт Pascal/DelphiАвтор FAQ
 Аватар для volvo
33405 / 21515 / 8236
Регистрация: 22.10.2011
Сообщений: 36,917
Записей в блоге: 12
29.07.2015, 12:51
Цитата Сообщение от Staut Посмотреть сообщение
тогда все будет "OK".
Без обнуления элементов массива тоже все будет Ок. То, что ты в каждой своей программе делаешь лишние действия по обнулению элементов - не значит, что их обязательно нужно делать.
0
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
29.07.2015, 13:17
- volvo, у меня действительно, как и у nick42, тоже при повторном нажатии клавиши - сплошной AV !
Чтобы не было путаницы и недопонимания, вот код:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
//##### ..... #####
// глобально. матрица Указателей на все BitMap-ы.
Graphics::TBitmap*  Bitmap_elps[8][10];
 
//##### ..... #####
// конструктор.
__fastcall  TForm1::TForm1(TComponent* Owner)
  : TForm(Owner)
{
  // созданре всех BitMap-ов.
  for ( int i=0; i<8; i++ )
  {
    for ( int   j=0; j<10; j++ )
    {
      Bitmap_elps[i][j] = new  Graphics::TBitmap;  // заполнение массива.
    }
  }
}
 
// .........
void __fastcall  TForm1::Button1Click(TObject *Sender)
{
  // удаление всех BitMap-ов.
  for ( int  i=0; i<8; i++ )
    for ( int  j=0; j<10; j++ )
    {
      delete  Bitmap_elps[i][j];
      Bitmap_elps[i][j] = NULL;  //( !!!!! )
    }
}
- Да так и должно быть: ведь первый раз Вы удаляете все BitMap-ы по их указателям из ячеек массива, а сами указатели, хотя уже и никуда не указывают, а продолжают оставаться не нулевыми!
- При повторном нажатии на клавишу Вы снова пытаетесь удалять (по ненулевым указателям) BitMap-ы, но их то уже НЕТ !

- Без строчки 28-кода при повторном нажатии клавиши - сплошной AV !
1
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
29.07.2015, 14:12
Staut, спасибо. Объяснением удовлетворен. Но непонятки на этом не кончились... Судите сами: поначалу было Access Violation при повторном нажатии Del-кнопки. Добавил строчку с обнулением. Ошибка исчезла. Вернул все обратно (для проверки), перекомпилировал. Теперь при повторном нажатии - Invalid Pointer Operation; программа слетает, но процесс остается в памяти. ... Перегрузился. Почистил папку с проектом (*.tds, *.obj); перекомпилировал... - Invalid Pointer Operation !
Пойду напьюсь... .
0
Почетный модератор
Эксперт С++
 Аватар для SatanaXIII
5851 / 2862 / 392
Регистрация: 01.11.2011
Сообщений: 6,906
29.07.2015, 16:23
Съезжает злой мужик с квартиры. Приходят к нему вандалы-анархисты, чтобы помочь с переездом, а он им показывает на окна и говорит: "выбейте нафик вот эти все окна, они мне больше не нужны".
Проходит время и в ту же квартиру вселяется семья спелеологов-визажистов. Живут себе, никого не трогают, но вдруг однажды, в холодное декабрьское утро раздается леденящий душу звонок в дверь. Папа-визажист несмелой рукой открывает входную дверь, а там стоит, и смотрит прямо на него, злой мужик. И за спиной его бригада вандалов-анархистов.

В главных ролях:
Злой мужик - Мистер Проппер
Вандалы-анархисты - Джорж Клуни и Марк Дакаскас
Окна - массив удаляемых данных
Менты, ластающие вандалистов - операционная система



Ну а на самом деле, происходит попытка удаления чужой уже памяти. В первый раз программа сообщила, посредством функции delete, что данная память именно ей уже больше не нужна. Но указатели на эту память не забыла. И при повторном вызове delete она уже требует удалить память, возможно, выделенную другой программе. Соответственно хрен ей кто это даст сделать. Ну или как-то так все это.
2
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
29.07.2015, 16:52
- nick42, прошу меня простить! Когда я писал AV, я имел в виду условно "ошибку рантайма".
Фактически у меня тоже вылетало: - "Invalid pointer operation" ! Конечно в таких дисциплинах, как
программирование, надо быть максимально конкретным. Еще раз извините. Так что и у меня в XE3 то-же,
что и у Вас.
- Если описать весь мой эксперимент полностью, то он следующий: (код весь мой Вы видели)

- 1) Представьте, что в "конструкторе" - НИЧЕГО НЕТ и в "обработчике клавиши" - оператора обнуления
указателя (Bitmaps_...[][] = NULL; ) тоже НЕТ.
- При нажатии на клавишу (вижу в отладчике) все указатели во всем массиве == NULL. Поэтому клавишу
можно нажимать миллион раз - никакого удаления НЕТ.

- 2) Добавляю в "конструктор" - создание всех BitMap-ов !
- Теперь при нажатии клавиши (вижу в отладчике) все указатели во всем массиве != NULL.
Поэтому при первом нажатии все уничтожается как надо! Но указатели-то остались хранящими прежнюю информацию
(т.е. не нулевыми). И, следовательно, при втором и т.д. нажатиях вылетает "Invalid pointer operation".

- 3) Добавление в "обработчик клавиши" оператора обнуления указателя (Bitmaps_...[][] = NULL; ) - полностью решает эту проблему.

Вроде все логично ...

- Хотя мне, почему-то, больше нравится вариант с блокировкой клавиши:
- 1) В "конструкторе" ставим оператор - (Button->Enabled = false; // еще не чего удалять.)
- 2) Там, где создаются все BitMap-ы, ставим оператор - (Button->Enabled = true; // разрешить удаление.)
- 3) В самом обработчике клавиши ставим оператор - (Button->Enabled = false; // запретить удаление, только-что все удалили.)

- Хотя, опять-же, это, если данная клавиша не выполняет кроме удаления BitMap-ов каких-либо других
действий
...

Добавлено через 5 минут
- SatanaXIII, совершенно согласен! Я о том-же самом, только очень длинно и излишне натуралистично!
0
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
29.07.2015, 21:10
Цитата Сообщение от Staut Посмотреть сообщение
очень длинно и излишне натуралистично!
Моё мнение - это НЕ МЕШАЕТ!! Как будто в модераторах сидят заскорузлые, поседевшие от подковерной борьбы за кресло деканы IT-факультетов!... Обыденности и так хватает (в обыденной жизни).
Всем спасибо за разъяснения. Кстати, выпив, я рассудил трезво, что неповторяемость сообщений тоже объяснима..., - Реакция системы на ошибочную ситуацию зависит от состояния этой самой системы: заполненность стэка, остаток выделенной памяти и т.д. - это всё величины переменные, зависящие от текущего момента. Поэтому глупо ожидать одинаковой реакции в разные моменты времени, пытаясь свести всё в строгую систему, - не для того Билл Гейтс набрал в свою команду сплошь демократов со "свободной подвеской" мозгов.
Да, и напоследок еще вопрос от дилетанта: вот такая запись на удаление массива что делает? __
C++
1
  delete [] massiv;
Я пробовал примениь ее в данном случае; ошибки не показало, но и память не высвобождалась.
0
 Аватар для BRcr
4043 / 2333 / 292
Регистрация: 03.02.2011
Сообщений: 5,066
Записей в блоге: 10
29.07.2015, 22:02
nick42, это удаление массива, память под который была выделена, как под массив.
Пример:
C++
1
2
3
int *i( new int[666] );
//...
delete[] i;
1
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
30.07.2015, 09:46
- nick42, в конце концов процессор, замученный нашими проблемами, тоже мог сходить "выпить"!
Отсюда и "неповторимость ответов"...

- Что касается Вашего примера: - delete [] massiv;, то на мой взгляд этого делать никак нельзя!
volvo Вас за это серьезно отругал бы, и был бы абсолютно прав!
Цикл volvo удаляет из памяти не массив Bitmaps_...[][], а конкретные экземпляры Bitmap-ов, на которые
указывают указатели, хранящиеся в массиве Bitmaps_...[][].

Удалив конкретный Bitmap, по указателю лежащему в ячейке, например, Bitmaps_...[0][3], надо не забыть очистить
этот указатель, т.к. он уже ни на что не указывает! Bitmaps_...[0][3] = NULL;

- Сам-же массив Bitmaps_...[][], как совершенно правильно писал volvo, статический! Его удалять НЕЛЬЗЯ !
Он будет удален АВТОМАТИЧЕСКИ при завершении приложения !

- Данную тему вообще-то правильнее было бы назвать не "Удаление двухмерного массива", а "Удаление ИЗ
двухмерного массива". В этом вся сущность ошибки !
1
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
30.07.2015, 09:54
Как я понял, для двумерного массива - это не подходит, без дополнительных циклов. Но одномерный массив (я проверял на байтовом массиве) по примеру BRcr удаляет корректно, так что, думаю, так делать можно.
0
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
30.07.2015, 09:54
- В примере BRcr массив (i) тоже выделяется динамически, как и сами Bitmap-ы. Его можно,
и даже нужно удалять, как только он перестает быть нужным. BRcr так и делает: delete [] i;
- В моем-же листинге, массив Bitmaps...[][] - выделяется статически и заботиться о его удалении
не надо.
0
Практикантроп
 Аватар для nick42
4841 / 2726 / 534
Регистрация: 23.09.2011
Сообщений: 5,798
30.07.2015, 10:07
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
//---------------------------------------------------------------------------
     char *msv;
//---------------------------------------------------------------------------
void __fastcall TForm1::Button1Click(TObject *Sender)
{
     msv = new char[0x100000] ;
     int i=0; while(i<0x100000) msv[i++]=0x56;
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Button2Click(TObject *Sender)
{
     delete [] msv;
}
//---------------------------------------------------------------------------
В этом примере та же петрушка: первый клик удаляет, но последующие дают ошибку.

Добавлено через 5 минут
P.S. Пока не добавишь вслед за delet'ом msv = NULL .

Добавлено через 3 минуты
ну, и хватит об этом, а то тему перенесут в "для начинающих"...
0
98 / 81 / 14
Регистрация: 26.07.2013
Сообщений: 596
30.07.2015, 15:32
- nick42, да все логично !
- 1) Вы создаете глобальный указатель. Статический.

- 2) В "обработчике кнопки 1" Вы:
a) создаете (динамически, из кучи) и вешаете на этот глобальный указатель большой массив.
b) заполняете его одинаковыми символами.

- 3) В "обработчике кнопки 2" Вы: удаляете этот динамический массив (отдаете память массива опять в кучу).

- Но глобальный, статический указатель на этот, уже не существующий большой массив, по прежнему указывает
на что-то из кучи. Данный проект уже мог запросить из кучи новый массив и куча выделила его как раз в физически
той-же, динамической памяти. Так что наш глобальный указатель указывает теперь на что-то совсем другое!
- Если Вы теперь снова захотите удалить что-то по этому указателю, то уже будете покушаться на какую-то другую
часть проекта, какую, совсем неизвестно ! Рантайм ошибка и не позволяет Вам это сделать !

А вообще-то, действительно, надо прекращать. Могут подумать, что мы "дуркуем". Это сейчас так модно ...
Так сейчас развлекаются, а этот форум не для этого !
0
30.07.2015, 21:58

Не по теме:

Staut, читая посты с обилием восклицательных знаков, я не вольно представляю себе человека, выведенного из равновесия. Кровь прилила к лицу, на виске бешено пульсирует венка, широко распахнутые глаза стреляют с одного оппонента на другого, речь то и дело переходит на крик... Это я так, в порядке лирики. :)

0
31.07.2015, 11:50

Не по теме:

- BRcr, процентов на 20 так и есть. (Без воскл. знака.)

0
31.07.2015, 12:33

Не по теме:

А обилие точек в тексте заставляет меня представлять человека, не совсем уверенного в себе. :p

0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
31.07.2015, 12:33
Помогаю со студенческими работами здесь

Удаление из двумерного массива
создаю двумерный массив таким образом &lt;script type=&quot;text/javascript&quot;&gt; function matrixArray(rows, columns) { var min =...

Удаление строк из двумерного массива
Помогите выполнить задание: Удалить все строки из двумерного массива, в которых второй элемент больше предпоследнего. Нужно вывести...

Удаление строк из двумерного массива
Подскажите, пожалуйста, как исправить код, чтобы удалялись только те строки, что поэлементно меньше. Т.е.т.е. 1 4 5 3 и 1 3 5 2 ...

удаление строк из двумерного массива
помогите написать программу с помощью процедур из 2-х матриц порядка N удалить строки которые совпадают в обоих матрицах.

удаление элементов из двумерного массива
в двумерном массиве, элементы которого- целые числа, удалить все строки, в которых нет ни одного чётного элемента.


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Новые блоги и статьи
модель ЗдравоСохранения 8. Подготовка к разному выполнению заданий
anaschu 08.04.2026
https:/ / github. com/ shumilovas/ med2. git main ветка * содержимое блока дэлэй из старой модели теперь внутри зайца новой модели 8ATzM_2aurI
Блокировка документа от изменений, если он открыт у другого пользователя
Maks 08.04.2026
Алгоритм из решения ниже реализован на примере нетипового документа, разработанного в конфигурации КА2. Задача: запретить редактирование документа, если он открыт у другого пользователя. / / . . .
Система безопасности+живучести для сервера-слоя интернета (сети). Двойная привязка.
Hrethgir 08.04.2026
Далее были размышления о системе безопасности. Сообщения с наклонным текстом - мои. А как нам будет можно проверить, что ссылка наша, а не подделана хулиганами, которая выбросит на другую ветку и. . .
Модель ЗдрввоСохранения 7: больше работников, больше ресурсов.
anaschu 08.04.2026
работников и заданий может быть сколько угодно, но настроено всё так, что используется пока что только 20% kYBz3eJf3jQ
Дальние перспективы сервера - слоя сети с космологическим дизайном интефейса карты и логики.
Hrethgir 07.04.2026
Дальнейшее ближайшее планирование вывело к размышлениям над дальними перспективами. И вот тут может быть даже будут нужны оценки специалистов, так как в дальних перспективах всё может очень сильно. . .
Горе от ума
kumehtar 07.04.2026
Эта мне ментальная установка, что вот прямо сейчас, мол, мне для полного счастья не хватает (нужное вписать), и когда я этого достигну - тогда и полный кайф. Одна из самых сильных ловушек на пути. . . .
Использование значений реквизитов справочника в документе, с определенными условиями и правами
Maks 07.04.2026
1. Контроль срока действия договора Алгоритм из решения ниже реализован на примере нетипового документа "ЗаявкаНаРаботу", разработанного в конфигурации КА2. Задача: уведомлять пользователя, если. . .
Доступность команды формы по условию
Maks 07.04.2026
Алгоритм из решения ниже реализован на примере нетипового документа "СписаниеМатериалов", разработанного в конфигурации КА2. Задача: сделать доступной кнопку (команда формы "ЗавершитьСписание") при. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru