Southmountain Ответов: 4

Что произошло с размером класса или объекта в visual C++ ?


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

Что я уже пробовал:

вот моя демо-версия:
#include <iostream>
using namespace std;

class Box
{
public:
	double m_height;
	double m_width;
	double m_length;

	double volume()
	{
		double volume = 0;
		volume =m_height * m_width*m_length;
		return volume;
	}

	Box()
	{
		m_height = 0;
		m_width = 0;
		m_length = 0;
		cout << "inside constructor:" << endl;
	}
};

int main()
{
	Box myBox;

	//cout << "Box attribute m_height:" << myBox.m_height;

	cout << "size of Box:" << sizeof(Box) << endl;
	cout << "size of myBox instance :" << sizeof myBox << endl;

	return 0;
}


Я получил это на своем экране вывода:
inside constructor:
size of Box:24
size of myBox instance :24

4 Ответов

Рейтинг:
21

Rick York

The sizeof operator pertains solely to size of the data. This is because when you copy an object only data is copied. Code does not need to be copied so it is not included in the total. This is due to the nature of how a __thiscall function is invoked. The term refers to how a method of a class is called - the object's "this" pointer is implicitly passed to the method. In the Visual Studio X86 compilers it was passed in the ECX register but that is implementation-specific. What all of this means is c++ code does not move. It is placed in memory by the OS's loader and when one calls a method the location of the object's data is passed to the method. That means data can be moved around and dynamically allocated but the location of the code that operates on it does not change so the code does not need to be moved or accounted for when an object is copied or created.


Southmountain

кристально ясно для меня! Спасибо!

Рейтинг:
2

Patrice T

Цитата:
Я протестировал простой класс и попытался найти его размер. похоже, что только члены данных вносят свой вклад в размер класса/объекта. где размер функций-членов?

Да, вы нашли его. Объект (экземпляр класса) содержит только элементы данных.
Причина, по которой код функции-члена не дублируется, заключается в том, что он остается неизменным для всех экземпляров этого класса/объекта, и компилятор знает об этом.
Цитата:
каково обоснование того, что эти члены не учитываются в размере класса/объекта?

Независимо от количества экземпляров одного и того же объекта, существует только 1 копия функций-членов.


Southmountain

Спасибо!

Рейтинг:
1

OriginalGriff

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


Southmountain

Спасибо, ОГ!

Рейтинг:
0

Greg Utas

Если класс имеет таковые virtual функции, которые он или другой класс переопределяет, первый член класса является указателем, который предшествует его другим членам данных. Этот указатель (часто называемый a vptr) ссылки на таблицу virtual функции (часто называют vtbl) ассоциируется с этим классом. Каждый класс, который наследует (а также тот, который определяет) любой из них virtual функции также будут иметь свои собственные vtbl. Записи в vtbl являются ли указатели функций ссылками на соответствующую реализацию каждого из них virtual функция для этого конкретного класса. Так что же происходит "под капотом", когда вы вызываете obj->func(args) является

auto vtbl = obj->vptr;
vtbl[index of func](obj, args); // obj is "this"
Индекс func жестко закодирован компилятором, который также создает каждый vtbl, после чего компоновщик собирает весь этот материал, чтобы загрузчик мог поместить его в память при запуске программы.


Southmountain

спасибо, что объяснили эту штуку vtbl! Теперь я припоминаю...