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

С++ для начинающих

Войти
Регистрация
Восстановить пароль
 
 
Рейтинг: Рейтинг темы: голосов - 13, средняя оценка - 4.69
Svinina
5 / 5 / 0
Регистрация: 28.11.2010
Сообщений: 81
#1

Можно ли несколько раз делитить область памяти? - C++

19.11.2011, 18:53. Просмотров 1675. Ответов 42
Метки нет (Все метки)

Собственно, чреват ли ошибками код:
C++
1
2
3
4
5
6
7
8
int *a;
 
a = new int[2];
a[0] = 1;
a[1] = 2;
 
delete [] a;
delete [] a;
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
19.11.2011, 18:53     Можно ли несколько раз делитить область памяти?
Посмотрите здесь:

Можно ли в С++ выделить память под объект в заданную мной область памяти? - C++
Есть код static inline void convertFromTextAlternative(quint8* dst, const QVariant& src){ QString *a = new...

Копирование область памяти - C++
Здравствуйте, у меня не получается прочитать/скопировать память в переменную. Я делаю .dll, так вот записать значения в адрес я смог, а...

Разделяемая область памяти - C++
Здравствуйте. Нам задали такое задание - написать программку(ки, ибо больше одного запущенного процесса) и запустить, чтобы выполнилось...

Динамическая область памяти функции new - C++
Чистый Си У кого есть варианты с пояснениями Написать пользовательскую функцию, решающую указанную ниже задачу. Массив создается в...

Указатель на конкретную область памяти - C++
Есть такая программа ArtMoney, с её помощью мы ищем адрес в памяти, затем изменяем значение по указателю, чтобы изменить количество игровой...

Закачка файла и перевод в область памяти типа PVOID - C++
В общем моя программа скачивает библиотеку, грузит ее в память и из памяти библиотека грузится в процесс посредством manual mapping. Но...

Bin файл из Modbus. Прочитать из файла область памяти - C++
Доброго времени суток! Подскажите пожалуйста, у меня есть bin-файл из которого нужно достать данные полученные устройством и хранящиеся...

После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
Svinina
5 / 5 / 0
Регистрация: 28.11.2010
Сообщений: 81
19.11.2011, 19:45  [ТС]     Можно ли несколько раз делитить область памяти? #21
Собственно, попробовал запустить этот код, компилятор (Qt'шный) не стал ругаться, программа отработала корректно.
Так где собака то зарыта?
Jupiter
Каратель
Эксперт С++
6552 / 3972 / 226
Регистрация: 26.03.2010
Сообщений: 9,273
Записей в блоге: 1
Завершенные тесты: 2
19.11.2011, 19:51     Можно ли несколько раз делитить область памяти? #22
Svinina, нигде, код абсолютно корректный
Svinina
5 / 5 / 0
Регистрация: 28.11.2010
Сообщений: 81
19.11.2011, 19:53  [ТС]     Можно ли несколько раз делитить область памяти? #23
Ну Берс в самом начале написал, что такой код чреват ошибками.
Вот и интересуюсь, какими=)
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 19:54     Можно ли несколько раз делитить область памяти? #24
Цитата Сообщение от Bers Посмотреть сообщение
Нет никакой гарантии, что NULL - это ноль.
Есть гарантия, что NULL - это невалидный спецадрес, обозначающий, что указатель ни куда не указывает. И усматривают здесь изготовители не компиляторов, всё зависит от начального адреса памяти. На IBM совместимых это должен быть ноль, не зависимо от компиляторов и даже от языков, а сигнальные камни любят память с ноля начинать, а если так сделано, то NULL не имеет права быть нолём, опять таки даже в том случае, если кроскомпилятор прошивок таких коммутаторов выпустит мелкософт.
Bers
Заблокирован
19.11.2011, 19:57     Можно ли несколько раз делитить область памяти? #25
Цитата Сообщение от Svinina Посмотреть сообщение
Ну Берс в самом начале написал, что такой код чреват ошибками.
Вот и интересуюсь, какими=)

Первый раз delete освобождает память. С этого момента, этот кусок памяти становится "свободным". И система в любой миг может отдать его ещё кому нибудь.

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

Добавлено через 55 секунд
taras atavin, да я уже вразумел)

NULL всегда не_валидный адрес, но не всегда является нулём)
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 19:58     Можно ли несколько раз делитить область памяти? #26
Цитата Сообщение от Jupiter Посмотреть сообщение
в Си NULL это ноль приведенный к void* в C++ NULL это ноль
Не ноль, а невалидный номер байта. На IBM совместимых гарантировано невалидный номер байта - это ноль, но если сдеать c, или c++ кроскомпилятор для сиганального камня, то там может быть и другое значение NULL.
Bers
Заблокирован
19.11.2011, 20:00     Можно ли несколько раз делитить область памяти? #27
Цитата Сообщение от taras atavin Посмотреть сообщение
Не ноль, а невалидный номер байта.
Именно ноль, и если я правильно понял, именно из-за этого и был принят nullptr
(что бы различать int равный нулю и void* равный нулю)
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 20:01     Можно ли несколько раз делитить область памяти? #28
Цитата Сообщение от Bers Посмотреть сообщение
Говорят: пиши тогда уж просто ноль. Так будит безопаснее.
Опаснее. И именно потому, что NULL - это не всегда ноль.
Jupiter
19.11.2011, 20:25
  #29

Не по теме:

Цитата Сообщение от Bers Посмотреть сообщение
Второй раз delete пытается освободить уже чужую память. И если эта память принадлежит уже кому то там - может произойти порча данных (хотя скорее всего система этот косяк пофиксит, и заломает накосячевший процесс)
таки Bers прав, признаю свою ошибку в 22 посту

taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 20:40     Можно ли несколько раз делитить область памяти? #30
Цитата Сообщение от Bers Посмотреть сообщение
Гарантированно оно, если delete []a; a=0;
Не?
А если дефайн - никаких гарантий нет.
Наоборот. Если NULL!=0, то по
C++
1
2
a=0;
delete [a];
очень даже произойдёт. А если дефайном, то вопрос только в правильности дефайна, ну так не пользуйся не правильным и при любом значении NULL ничего не произойдёт. Кстати, я никогда не полагаюсь на проверку внутри delete, а всегда пишу явно
C++
1
2
3
4
if (p)
{
 delete [] p;
}
Bers
Заблокирован
19.11.2011, 20:41     Можно ли несколько раз делитить область памяти? #31
Я такую запись не понимаю:
Цитата Сообщение от taras atavin Посмотреть сообщение
delete [a];
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 21:04     Можно ли несколько раз делитить область памяти? #32
Цитата Сообщение от Bers Посмотреть сообщение
не сказать, что хорошо знаю стандарт, но помойму, там идёт проверка на ноль, а не на NULL
На значение NULL без обращения упоминания имени данного макроса, так как проверять просто на ноль нельзя: если ноль - валидный адрес, то это может привести к невозможности выделить память.

Добавлено через 13 минут
Цитата Сообщение от Bers Посмотреть сообщение
Первый раз delete освобождает память. С этого момента, этот кусок памяти становится "свободным". И система в любой миг может отдать его ещё кому нибудь.
Второй раз delete пытается освободить уже чужую память. И если эта память принадлежит уже кому то там - может произойти порча данных
. Нет. Ни каких чужих данных там быть не может: в многозадачных осях все программы работают в виртуальных адресных пространствах, а освобожденная память из них изымается, то есть виртуальный адрес после освобождения становится столь же невалидным, как и NULL, кусок же памяти по тому же физическому адресу, который как раз может быть выдан кому то ещё, после такого выделения окажется в другом виртуальном адресном пространстве, так как они все локальны, глобальны только физические адреса, а в однозадачной системе просто больше никого нет, кому могла бы быть выдана память по тому же адресу. Опасно же второй раз удалять не подряд, если та же самая прога и тот же её екземпляр успеет получить кусок памяти, на который попадёт тот же адрес.
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
... f1(...)
{
 static ... *p;
 ...
 p=new ...;
 ...
 delete [] *p;  // Эта строчка выполнилась дважды в разные вызовы f1, а между ними p попал в память выданную f2
}
... f2(...)
{
 static ... *p;
 ...
 p=new ...; 
 ...
 delete [] *p;
}
. И всё таки дважды делитить можно в единственном случае: если между делитами было ещё одно выделение памяти с того же начального адреса.

Добавлено через 4 минуты
То есть
C++
1
2
3
4
5
6
7
8
int *p;
p=new int [...];
...
delete [] p;
...
p=new int [...];
...
delete [] p;
можно.
Svinina
5 / 5 / 0
Регистрация: 28.11.2010
Сообщений: 81
19.11.2011, 21:08  [ТС]     Можно ли несколько раз делитить область памяти? #33
в многозадачных осях все программы работают в виртуальных адресных пространствах, а освобожденная память из них изымается, то есть виртуальный адрес после освобождения становится столь же невалидным, как и NULL
А вот тут можно поподробнее?
Правильно ли я понимаю, что один раз выделив память, а затем ее освободив, физически к этой области памяти процесс уже доступа получить никогда не сможет?
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 21:17     Можно ли несколько раз делитить область памяти? #34
Цитата Сообщение от Bers Посмотреть сообщение
Именно ноль, и если я правильно понял, именно из-за этого и был принят nullptr
Нет. Имплементейшн дефайн - это как раз и есть не всегда ноль. А nullptr приняли, чтоб избавиться от макроса в неконтролируеммом заголовке. У меня где то был исходник для убунты, начинающийся с
C++
1
#define NULL 0
, дефайн этот я написал собственноручно, так вот, если такое начало будет в исходнике для сигнального камня, то получим полную фигню. Компилятор и так должен соответствовать архитектуре, не только по значению NULL, а дефайн может быть в любом "левом" заголовке и даже прямо в исходнике, автор которого архитектуру мог не только не учитывать, а ещё и делать для другой архитектуры. Константа же, известная самому компилятору, а не препроцессору, не будет зависеть от таких самодельных дефайнов, а только от компилятора.

Добавлено через 4 минуты
Цитата Сообщение от Bers Посмотреть сообщение
delete [a];
Я тоже эту очепятку не понимаю. Должно быть
C++
1
delete [] a;
Bers
Заблокирован
19.11.2011, 21:18     Можно ли несколько раз делитить область памяти? #35
taras atavin,
C++
1
2
3
4
5
6
7
void Foo(int a) {...}
void Foo( void* ptr) {...}
 
...
 
Foo(0); //угадай, какая из функций будит запущена?
           //если угадаешь правильно, поймёшь, зачем нужен nullptr_t
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 21:26     Можно ли несколько раз делитить область памяти? #36
Цитата Сообщение от Svinina Посмотреть сообщение
А вот тут можно поподробнее?
Правильно ли я понимаю, что один раз выделив память, а затем ее освободив, физически к этой области памяти процесс уже доступа получить никогда не сможет?
Почему "никогда"? К этой памяти можно обратиться, если:
1. Освобождённый адрес находится на странице, содержащей другой, валидный локальный адрес. В этом случае освобожденный адрес тоже должен стать невалидным, но система не в состоянии этого гарантировать. Но память на одной странице не может быть выдана разным процессам, так что чужую память ты таким образом не освободишь и к ней не обратишься.
2. Если память была повторно выделена процессу.

Добавлено через 2 минуты
Цитата Сообщение от Bers Посмотреть сообщение
void Foo(int a) {...}
void Foo( void* ptr) {...}
...
Foo(0); //угадай, какая из функций будит запущена?
* * * * * *//если угадаешь правильно, поймёшь, зачем нужен nullptr_t
C++
1
2
3
4
5
#define NULL 0xFFFF
void Foo(int a) {...}
void Foo( void* ptr) {...}
...
Foo(0); //А здесь? Если NULL дефайнить числом, то и здесь проблема та же, дело не в ноле.
Это ещё одна цель введения nullptr.
Bers
Заблокирован
19.11.2011, 21:29     Можно ли несколько раз делитить область памяти? #37
Цитата Сообщение от taras atavin Посмотреть сообщение
Foo(0); //А здесь?
Константа не_ноль интерпритируется как инт по умолчанию. Естественно первый вариант
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 21:47     Можно ли несколько раз делитить область памяти? #38
Цитата Сообщение от Bers Посмотреть сообщение
Естественно первый вариант
Первый и должен, так как аргумент - число. Но и NULL - тоже число, то есть foo(NULL) вызовет первый вариант, а программист имеет ввиду второй. Если аргумент - переменная указательного типа, то вызовется второй вариант, как и должно быть. Целей может быть много, но в данном случае на самом деле всё таки одна - избавиться от макроса. Почему надо от него избавиться - это уже другой вопрос и проблема со многими аспектами. Возможность ошибочного дефайна - один из них. Второй - вызов перегруженной функции с невалидным указателем, если есть версия c интом. Чтоб не писать
C++
1
2
int *p=NULL;
foo(p);
. Кстати, а как будет здесь:
C++
1
2
3
4
5
6
7
#define NULL (void*)0xFFFF
void foo(int x);
void foo(void *p);
void foo(int *p);
...
foo(0);
foo(NULL);
и здесь:
C++
1
2
3
4
5
6
void foo(int x);
void foo(void *p);
void foo(int *p);
...
foo(0);
foo(nullptr);
? Валидные указаетели все имеют типы, так как являются переменными. Указатель-переменная с невалидным значением тоже имеет тип. А как быть с nullptr? Ведь программист может под этой константой подразумевать невалидный указатель на что угодно, причём ещё и не всегда одно и тоже в разных местах программы.
Bers
Заблокирован
19.11.2011, 21:48     Можно ли несколько раз делитить область памяти? #39
Цитата Сообщение от taras atavin Посмотреть сообщение
А как быть с nullptr?
эта волшебная константа типа nullptr_t
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
19.11.2011, 21:51     Можно ли несколько раз делитить область памяти?
Еще ссылки по теме:

Возможно ли узнать, существуют ли другие указатели на данную область памяти? - C++
Возможно ли узнать, существуют ли другие указатели на данную область памяти? например: char * pChar = new char; //init ...

Ссылка, Указатель, Область памяти выделенная оператором new для указателя - C++
Подскажите пожалуйста, как сделать ссылку на область памяти выделенную оператором new для указателя читая книгу Джесса Либерти в...

Есть ли способ проверить, сколько указателей указывают на определённую область памяти? - C++
Привет народ. Такой вопрос: Есть ли способ проверить, сколько указателей указывают на определённую область памяти? Спасибо.

Увеличение чисел в несколько раз - C++
Здравствуйте. Сразу же извиняюсь за свой "тупой" вопрос, я в С++ недавно так что помогите. Как увеличить число в 2 раза. Например я ввожу...

goto проходит несколько раз - C++
Есть код: int main() { char pwd; pwd: printf("> "); getline(pwd,15); if(strstr(pwd,"1234567")) {if(pwd!=ch-1+'0')...


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

Или воспользуйтесь поиском по форуму:
taras atavin
Ушёл с форума.
3569 / 1752 / 91
Регистрация: 24.11.2009
Сообщений: 27,619
19.11.2011, 21:51     Можно ли несколько раз делитить область памяти? #40
Кстати, студия 2008 не знает ни nullptr, ни NULL_PTR, ни null_ptr, ни NULLPTR.
Yandex
Объявления
19.11.2011, 21:51     Можно ли несколько раз делитить область памяти?
Ответ Создать тему
Опции темы

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