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

C++

Войти
Регистрация
Восстановить пароль
 
 
Рейтинг: Рейтинг темы: голосов - 68, средняя оценка - 4.74
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
#1

[C++] Взятие адреса конструктора. Физическое время существование объекта. - C++

16.02.2012, 15:40. Просмотров 8306. Ответов 69
Метки нет (Все метки)

1. конструктор.

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
class A
{
 
int a;
public:
A():a(555){};
~A(){}
 
};
 
int main()
{
A* pa = &A();//это вызов конструктора - явный. он используется контейнерами stl.
//вывод - конструктор можно вызвать явно и с параметрами и без.
// возвращается некий указатель на начало объекта
};
Вопрос: если объект начинается с конструктора, то полученный нами указатель - будет указывать на конструктор? и только высокоуровневые ограничения не дают нам видеть его среди членов объекта и работать с ней. Если это так, то спутившись на уровень ниже, туда где нет ограничений, по идее получив данный адрес - мы можем сделать call по этому адресу. другое дело какой эффект получится, непонятно.
поэтому обращаюсь к тебе Evg как к очень опытному специалисту знающему "нутро".
вот мы сделали бинарник. в нем программа, в ней создаются объекты классов.
мне сложно судить где буду лежать эти объекты, предположу что в .text
если мое предположение верно, то после отображения в память, можно будет обратится к конструктору зная его адрес, поскольку никакие высокоуровневые вещи не будут мешать.

вопрос 2

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
class A
{
public:
    int a;
A():a(555){};
~A(){}
 
};
 
int main()
{
A* pa = &A();//это временный объект и сразу после создания будет вызван деструктор
 
int mass [1000];
 
for(int i=0;i<1000;i++)//это вызовы для мебели и зачистки останков временных объектов
    mass[i] = i;
 
 
pa->~A(); //не вызывается. объекта нет НО
int z = pa->a; //дело его живет. z ==555
 
 
return 0;
};
каково время жизни поля класса после уничтожения объекта класса?
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
16.02.2012, 15:40     [C++] Взятие адреса конструктора. Физическое время существование объекта.
Посмотрите здесь:

Почему лучше инициализировать объекты класса во время инициализации конструктора? C++
Существование объекта C++
C++ Реализовать динамический массив объектов, учитывая, что параметры для конструктора у каждого объекта разные
ООП в C++: Вызов родительского конструктора с параметром при создании объекта дочернего класса C++
C++ Взятие адреса у константной переменной при объявлении
[Двусвязные списки] Добавление по индексу. Взятие адреса по индексу C++
C++ Взятие адреса в аргументе
После регистрации реклама в сообщениях будет скрыта и будут доступны все возможности форума.
Evg
Эксперт CАвтор FAQ
 Аватар для Evg
17188 / 5442 / 337
Регистрация: 30.03.2009
Сообщений: 14,758
Записей в блоге: 26
16.02.2012, 15:46     [C++] Взятие адреса конструктора. Физическое время существование объекта. #2
В личке ты вопрос ставил по другому. Просто сейчас повторю твой вопрос и ответ, который я написал, но не смог отправить. Если после этого тебе до сих пор не станет ясен ответ на вопрос 2 (уже из данной темы) - скажи. Про первый вопрос, как я уже писал, я вопроса не понял

Вопрос N2, как он был задан в личке

второй момент на который хотелось бы твоих комментариев. время жизни авто переменных.
каково оно? много раз написано на форуме что после выхода из области видимости и при отсутствии след вызовов - данные лежат нетронутыми. вопрос, какое количество последующих вызовов должно произойти чтобы данные затерлись, если данные эти - поля временного класса А, который создан и сразу уничтожен вначале моего письма.

Ответ

Я не знаю, насколько ты знаком с устройством файловой системы. Когда ты удаляешь файл на диске, то ты потом его можешь восставновить (если повезёт). Происходит это потому, что файл, как логическая сущность, из файловой системы на логическом уровне удаляется. Но физическое содержимое физического диска остаётся не тронутым. Удаляется только запись о том, что такой-то файл присуствует (именно поэтому после восстановления файлов у них нельзя восстановить оригинальное имя), но содержимое файла на диске остаётся, хотя это место отмечено как свободное. Если после удаления файла создать другой файл, то есть вероятность того, что данные от нового файла попадут на те же саме физические области физического диска и перетрут их (и тогда старый файл уже нельзя будет восстановить).

С твоим вопросом про объекты - то же самое. Логическое время жизни автоматического объекта (которое гарантировано стандартом) - это от точки его объявления до закрывающей фигурной скобки в том блоке, в котором объявлена переменная. После того, как перешли закрывающую скобку, логичеси объект существовать перестаёт. Но содержимое объекта физически находится в той области памяти, где существовал объект. Если эта область памяти затем кем-то переиспользуется, то данные от объекта навечно утеряны, если память ещё не успела поиспользоваться, то физически сами данные можно получить

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
#include <stdio.h>
 
int func1 (void)
{
  int a[10];
  a[7] = 0x11111111;
  return a[7];
}
 
int func2 (void)
{
  int b[10];
  /* Используем неинициализированные данные */
  return b[7];
}
 
int main (void)
{
  int x, y;
 
  x = func1();
  y = func2();
  printf ("%x %x\n", x, y);
  return 0;
}
Конкретно в данном случае при использовании конкретно gcc получилось так, что после завершения работы func1 память, в которой лежал массив "a", физически больше не переписывалась и не переиспользовалась. При входе в функцию func2 массив "b" попал в ту же самую память, где находился массив "a", а потому читая неинициализированное значение, мы на самом деле прочитали данные, которые когда-то соответсвовали массиву "a". И потому, читая b[7], прочитали то же значение, что было когда-то записано в a[7]

Ответ на вопрос "какое количество последующих вызовов должно произойти чтобы данные затерлись" нельзя дать однозначно. Это зависит от каждого конкретного случая и от того, каким образом компилятор распорядится стеком. Даные затрутся в тот момент, когда активация текущей функции наложится на интересующий тебя участок памяти и когда компилятор построит записи в эту память. В моём примере активации стека наложились, но в func2 из этой памяти я только читал, но не писал.
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 16:00  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #3
Evg, спасибо. ответ исчерпывающ.
первый вопрос разобъем.
1. указатель на объект указывает на что? на некую область памяти с которого стартует размещение объекта?
если первой в объекте идет функция - конструктора, значит ли это что получая указатель на объект - мы получаем и адрес расположения конструктора?
CheshireCat
Эксперт С++
2910 / 1238 / 78
Регистрация: 27.05.2008
Сообщений: 3,321
16.02.2012, 16:17     [C++] Взятие адреса конструктора. Физическое время существование объекта. #4
Сообщение было отмечено автором темы, экспертом или модератором как ответ
1. Да, указатель на объект указывает на некоторую область памяти, в которой размещен объект, - более детально, на первый (в традициях C/C++ правильнее, наверное, говорить "на нулевой") байт бинарного представления объекта.
2. Нет, независимо от наличия член-функций в объекте, этот указатель не указывает ни на конструктор, ни на какую-либо вообще член-функцию.
Более того, Стандарт языка говорит, что указатель на конструктор получать вообще не следует. (Ну, ладно, уточню: хакерскими методами его получить можно, но вот что произойдет при попытке вызвать конструктор по полученному указателю - об этом Стандарт скромно умалчивает.)
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 16:22  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #5
CheshireCat, ну собственно об этом и шла речь.
найти его по смещению и вызвать. просто думалось что оно совпадать может с началом.
но скорее всего вначале будут какие либо сигнатуры, может имя а может еще что
Bers
Заблокирован
16.02.2012, 16:38     [C++] Взятие адреса конструктора. Физическое время существование объекта. #6
Цитата Сообщение от AzaKendler Посмотреть сообщение
1. указатель на объект указывает на что?
Указатель на объект указывает на объект (адрес, с которого начинаются данные объекта)

Цитата Сообщение от AzaKendler Посмотреть сообщение
получая указатель на объект - мы получаем и адрес расположения конструктора?
Получая адрес объекта, мы получаем адрес объекта.

Рассмотрим код:

C++
1
2
3
&A(); //строчка содержит две операции:
        //1. Создание объекта.
        //2. Взятие адреса у сущности, получившейся в результате пункта 1
Таким образом, результатом выражения будет являться адрес объекта.

Рассмотрим другой пример:

C++
1
2
3
4
5
6
int foo() { } 
int main ()
{
    &foo;  //здесь мы получаем адрес самой функции, 
              //а не "результата" её работы
}
Рассмотрим 3й пример:

C++
1
2
3
4
5
6
7
8
9
10
11
12
struct test 
{ 
    test() {} 
    void foo(){}
};
 
 
int main ()
{
    &test::test;  //: error C2277: test::{ctor}: невозможно получить адрес этой функции-члена
    &test::foo;   //а так можно
}
Стоит различать что есть "результат вычисления выражения", что бы понимать, к чему именно будет применена следующая на очереди операция.

Добавлено через 1 минуту
Цитата Сообщение от CheshireCat Посмотреть сообщение
2. Нет, независимо от наличия член-функций в объекте, этот указатель не указывает ни на конструктор, ни на какую-либо вообще член-функцию.
Более того, Стандарт языка говорит, что указатель на конструктор получать вообще не следует. (Ну, ладно, уточню: хакерскими методами его получить можно, но вот что произойдет при попытке вызвать конструктор по полученному указателю - об этом Стандарт скромно умалчивает.)
можете привести пример, как именно срисовать указатель на конструктор, и затем вызвать этот конструктор по указателю?
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 17:01  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #7
Bers, ну в теории осмелюсь предположить что.
1. открываем исполняемый файл и ищем в тексте расположение искомого класса. запоминаем смещение относительно начала секции. далее смотрим смещение конструктора - чисто теоретически он будет первым после имен.
затем загружаем файл в память (н-м способом) получаем адрес модуля процесса этого файла, прибавляем смещение до секции (пусть с кодом) + смещение до объекта + смещение до конструктора. далее пробуем запустить.
процедура сходная с поиском функций в сторонней длл
Kastaneda
Форумчанин
Эксперт С++
 Аватар для Kastaneda
4253 / 2785 / 219
Регистрация: 12.12.2009
Сообщений: 7,109
Записей в блоге: 1
Завершенные тесты: 1
16.02.2012, 18:33     [C++] Взятие адреса конструктора. Физическое время существование объекта. #8
AzaKendler, по поводу того, на что указывает указатель на объект - посмотри код из первого поста В дизассемблерованном коде отсутствует позднее связывание. Оптимизация? правда тот код будет работать только в MSVS и только с вируатльными ф-циями (про другие компиляторы ни чего сказать не могу, т.е. не проверял) Но как пример сойдет)
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 18:54  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #9
Kastaneda, ну чтоб получился законченный пример я хочу попросить тебя дописать а что же получилось в результате настоящего позднего связывания. скинь плиз либо туда либо сюда
Evg
Эксперт CАвтор FAQ
 Аватар для Evg
17188 / 5442 / 337
Регистрация: 30.03.2009
Сообщений: 14,758
Записей в блоге: 26
16.02.2012, 19:22     [C++] Взятие адреса конструктора. Физическое время существование объекта. #10
Цитата Сообщение от AzaKendler Посмотреть сообщение
если объект начинается с конструктора
Наконец, как мне кажется, я понял твою ошиюку. Ты считаешь, что если в теле класса описан метод (или конструктор), то он "находится" в объекте. На самом деле это не так. В объекте находятся только данные (поля класса), а методы и конструкторы - по сути дела это обычные функции, просто описаны они в теле класса (что является всего лишь синтаксисом языка, не более того). В своей статье про конструкторы и деструкторы есть много аналогов, когда для кода на Си++ пишется код-аналог на Си. Собственно, в случае твоего вопроса это так же справедливо

Добавлено через 7 минут
Цитата Сообщение от AzaKendler Посмотреть сообщение
C++
1
A* pa = &A();//это вызов конструктора - явный. он используется контейнерами stl
Это НЕ явный вызов конструктора. Запись "A()" означает создать объект типа A и вызвать для него дефолтный конструктор, а "&A();" означает взятие адреса на этот объект
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 19:38  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #11
Evg, тогда поясни еще пожалуйста, куда в бинарном файле попадают методы объекта класса. они лежат отдельно от полей?
например у нас есть адрес начала "объекта" перемещаясь от этого начала мы находим..адрес? того где лежат его методы?
поясни плиз.
retmas
Жарю без масла
842 / 724 / 158
Регистрация: 13.01.2012
Сообщений: 1,671
16.02.2012, 19:42     [C++] Взятие адреса конструктора. Физическое время существование объекта. #12
методы класса - обычные ф-ии со своей сигнатурой.
объект - кусок памяти с данными и никакие ф-ии в этом объекте не "лежат"
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 19:43  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #13
retmas, в бинарнике. имелся ввиду бинарник и его разделы.
в любом случае надо прояснить вопрос. как оно там расположено и вызывается. в секции кода точка входа в программу. там же видимо лежит и конструктор?
Bers
Заблокирован
16.02.2012, 19:49     [C++] Взятие адреса конструктора. Физическое время существование объекта. #14
Цитата Сообщение от AzaKendler Посмотреть сообщение
Evg, тогда поясни еще пожалуйста, куда в бинарном файле попадают методы объекта класса. они лежат отдельно от полей?
например у нас есть адрес начала "объекта" перемещаясь от этого начала мы находим..адрес? того где лежат его методы?
поясни плиз.
Не существуют методов объекта класса. Существуют методы класса.
Живут они в статической области памяти. И "выглядят" как самые обычные функции.

После компиляции, вообще уже не существует никаких классов, и никаких экземпляров классов.
Только боевой код самих функций, и память.

Грубо говоря, исходный код вида: объект.Метод();
Преобразуется к виду Метод(this объекта);
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 19:53  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #15
Bers, ну понятно. важно понять теперь что куда попадает. если я правильно понимаю то все эти методы кучей попадут в секцию кода в бинарном файле. верно? возникает вопрос а сам класс будет трактован как просто набор данных? что же тогда будет его началом? на что мы возьмем указатель?

A* a = &A();
Bers
Заблокирован
16.02.2012, 19:55     [C++] Взятие адреса конструктора. Физическое время существование объекта. #16
Цитата Сообщение от AzaKendler Посмотреть сообщение
Evg, тогда поясни еще пожалуйста, куда в бинарном файле попадают методы объекта класса. они лежат отдельно от полей?
В самом бинарном файле присутствует только боевой код скомпилированных функций.
Никаких экземпляров классов, с его полями там нет.

Добавлено через 1 минуту
Цитата Сообщение от AzaKendler Посмотреть сообщение
A* a = &A();
Будит запущена функция A();
Результатом работы функции будит объект.

Далее: &объект
Результат работы - адрес объекта.

Что не понятного?
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 20:04  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #17
Цитата Сообщение от Bers Посмотреть сообщение
В самом бинарном файле присутствует только боевой код скомпилированных функций.
Никаких экземпляров классов, с его полями там нет.
конструктор - функция? поля - данные?

вопрос. получая указатель на созданный объект класса - получаем адрес чего?

Добавлено через 2 минуты
Цитата Сообщение от Bers Посмотреть сообщение
адрес объекта.
объекта нет. он существует на уровне с++, так на что указывает указатель? на данные? или на боевую функцию в памяти?
A* a = &A();

если на данные то в данных в бинарнике должен быть адрес того где искать конструктор. верно?
Bers
Заблокирован
16.02.2012, 20:06     [C++] Взятие адреса конструктора. Физическое время существование объекта. #18
Цитата Сообщение от AzaKendler Посмотреть сообщение
конструктор - функция? поля - данные?

вопрос. получая указатель на созданный объект класса - получаем адрес на что?
"Объект" на с++ это кусок памяти. (не путать с "экземплярами классов ООП" )

Указатель - это переменная, которая хранит адрес памяти.

Получая указатель, который хранит адрес созданного объекта, ты получаешь адрес этого объекта.
Адрес ячейки памяти, с которой начинается нулевой байт этого объекта.
AzaKendler
 Аватар для AzaKendler
214 / 116 / 9
Регистрация: 30.05.2011
Сообщений: 1,772
16.02.2012, 20:10  [ТС]     [C++] Взятие адреса конструктора. Физическое время существование объекта. #19
Цитата Сообщение от Bers Посмотреть сообщение
Адрес ячейки памяти, с которой начинается нулевой байт этого объекта
так что есть объект в терминах - "данные - боевые функции". что есть его нулевой байт? он в секции данных или кода?

сформулируй однозначное определение плиз. это важно. например объект класса с++ на уровне бинарного файла это:

поля объекта лежат в секции данных. методы в секции кода. в секции данных хранятся смещения до методов в секции кода.
методы естественно на таком уроне есть функции.

получая указатель на объект класса с++ мы получаем адрес некой сигнатуры (нулевой байт) этого класса в секции данных, далее подряд идут данные этого объекта

как то так.это интересно понять
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
16.02.2012, 20:13     [C++] Взятие адреса конструктора. Физическое время существование объекта.
Еще ссылки по теме:

C++ Зачем взятие адреса нулевого элемента массива, если сама переменная и так его содержит?
Получение адреса объекта после обнуления указателя на этот объект C++
C++ В чём отличия конструктора копирования и конструктора перемещения? Где и как их нужно использовать?
Используйте объект orange типа Tfruit для инициализации объекта grapefruit с помощью конструктора копирования C++
C++ Взятие значение из адреса

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

Или воспользуйтесь поиском по форуму:
retmas
Жарю без масла
842 / 724 / 158
Регистрация: 13.01.2012
Сообщений: 1,671
16.02.2012, 20:13     [C++] Взятие адреса конструктора. Физическое время существование объекта. #20
Цитата Сообщение от AzaKendler Посмотреть сообщение
retmas, в бинарнике. имелся ввиду бинарник и его разделы.
и я о том же
Цитата Сообщение от AzaKendler Посмотреть сообщение
а сам класс будет трактован как просто набор данных?
нет в бинарнике никаких классов
Цитата Сообщение от AzaKendler Посмотреть сообщение
получая указатель на созданный объект класса - получаем адрес чего?
адрес начала куска памяти, хранящей состояние(данные) объекта
Yandex
Объявления
16.02.2012, 20:13     [C++] Взятие адреса конструктора. Физическое время существование объекта.
Ответ Создать тему
Опции темы

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