问题
From what i know, the size of a class in c++ depends on the below factors -
- Size of all non-static data members.
- Order of data members.
- If byte padding is enabled or not.
- Size of its immediate base class.
- The existence of virtual functions.
- Mode of inheritance (virtual inheritance).
Now I've created 2 classes as below -
class A{
int a;
short s;
int b;
char d;
};// kept a char at last on purpose to leave a "hole"
class B : public A{
char c;
};
now on checking the size of A and B I see
- size of A: 16
- size of B: 16
my assumption is the char c in class B is accommodated in "hole" left in class A.
But, whats confused me is the below scenario wherein I make the members public
class A{
public:
int a;
short d;
int b;
char s;
};
class B : public A{
public:
char c;
};
Now the size becomes
- size of A: 16
- size of B: 20
I cannot seem to understand the reason for this difference.
回答1:
This is because the standard requires members with the same access control to be grouped together in memory. That grouping decides how the object gets padded so changing it can/will change the size of the object. A note for this can be found in [class.mem]/19
[ Note: Non-static data members of a (non-union) class with the same access control and non-zero size ([intro.object]) are allocated so that later members have higher addresses within a class object. The order of allocation of non-static data members with different access control is unspecified. Implementation alignment requirements might cause two adjacent members not to be allocated immediately after each other; so might requirements for space for managing virtual functions ([class.virtual]) and virtual base classes ([class.mi]). — end note ]
回答2:
The Itanium ABI uses the C++03 definition of POD to define classes that are "POD for the purposes of layout". Having private data members disqualifies a class from being an aggregate and therefore POD in C++03:
A POD-struct is an aggregate class that has no non-static data members of type non-POD-struct, non-POD-union (or array of such types) or reference, and has no user-defined copy assignment operator and no user-defined destructor.
Being a POD class disables tail padding reuse:
The dsize, nvsize, and nvalign of these types are defined to be their ordinary size and alignment. These properties only matter for non-empty class types that are used as base classes. We ignore tail padding for PODs because an early version of the standard did not allow us to use it for anything else and because it sometimes permits faster copying of the type.
Thus, in your first example, A is not a POD for layout purposes and its tail padding can be used for B::c, but in your second example, it is a POD, and its tail padding cannot be reused.
来源:https://stackoverflow.com/questions/58960303/why-does-the-size-of-class-in-c-depend-on-the-public-private-status-of-data-me