• Advertisement
Sign in to follow this  

C++: sizeof(class with virtual functions)

This topic is 4429 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hi if I have a class derived from a abstract base class in C++ like this
class base
{
public:
virtual void somefunction();
}

class derived : public base
{
public:
void somefunction();
unsigned int variable;
}

Does sizeof(derived) return 4 bytes for unsigned int variable or 4 bytes for uint.. plus the size of the vtable pointer?

Share this post


Link to post
Share on other sites
Advertisement
For 32bit x86 systems sizeof(base) == 4 and sizeof(derived) == 8 on almost any compiler.

Share this post


Link to post
Share on other sites
You can't rely on the size of a structure being the same between architectures, compilers, or even on the same compiler and architecture with different compile options.

That's why sizeof() exists, because the size of a structure is decided by the compiler at compile time.

Mark

Share this post


Link to post
Share on other sites
Quote:
Original post by Basiror
so the table pointer is included

thx alot


Yes, it's included. The C++ compiler basically introduces a hidden member for your class that contains the pointer to the vtable (depends much on how the compiler implements virtual functions).

Share this post


Link to post
Share on other sites
Now that you know the answer, I wonder why you want to know? There isn't much useful information that can be gotten out of the knowledge.

CM

Share this post


Link to post
Share on other sites
The nitpicky would tell you that how exactly virtual function lookup works is implementation-dependent and might not be based on vptrs at all.

Even for compilers that do use them once you throw multiple inheritance in the mix you can easily end up with multiple vptrs.

i.e. any use you make of the information coming out of this thread is compiler-dependent and could change even between versions of the same compiler.

Share this post


Link to post
Share on other sites
Quote:
Original post by Conner McCloud
Now that you know the answer, I wonder why you want to know? There isn't much useful information that can be gotten out of the knowledge.

CM


Actually, understanding that the compiler tacks on the hidden member is very useful, especially if you can find out how much is tacked on. This is important if you want to, for example, dump the entire class out to file as raw data (not serialized) and then hope to reconstruct the vftable when you reload it. Which is not something I recommend doing, btw ;)

Heck, anytime you're very concerned about space information like this is very useful =) In certain cases, knowing where the vftable member is placed in the object could also be extremely important :)

Just my 2c :)

Share this post


Link to post
Share on other sites
Quote:
Original post by Grafalgar
Actually, understanding that the compiler tacks on the hidden member is very useful, especially if you can find out how much is tacked on. This is important if you want to, for example, dump the entire class out to file as raw data (not serialized) and then hope to reconstruct the vftable when you reload it.

When would you want to do this?
Quote:
Original post by Grafalgar
Which is not something I recommend doing, btw ;)

Then how important can it be?
Quote:
Original post by Grafalgar
Heck, anytime you're very concerned about space information like this is very useful =) In certain cases, knowing where the vftable member is placed in the object could also be extremely important :)

Why would you want to do this?

When answering these questions, keep in mind the original poster is clearly a begginer who isn't ready for the sort of advanced topics such knowledge is useful for. If he were, he would have known how to answer that question himself.

CM

Share this post


Link to post
Share on other sites
Quote:
Original post by Conner McCloud
Now that you know the answer, I wonder why you want to know? There isn't much useful information that can be gotten out of the knowledge.

CM


We have to write a little database at university and in our newsgroup some people used sizeof(nonPOD type) to save and reload objects out of chunks loaded from the HD

So they would probably overwrite their vtable pointer which leads to segfaults every now and then

this might work when you don t restart the DB but once you restart and the program is mapped to another point in memory this might happen

Share this post


Link to post
Share on other sites
You might consider makeing a datastructur like this:

class myClass
{
private:
struct
{
// <whatever data goes here>
} myStoreableData;

// somevirtual functions
};

Then doing sth like fwrite (&myStoreableData, sizeof(myStoreableData), 1, fp)
would work without problems - you are not touching/overwriting the vtables.

Regards

Share this post


Link to post
Share on other sites
Or you could simply implement a Serialize() function in your class that may looks like this (may not compile):


class Record
{
protected:
int Value1;
int Value2
char* Name;

public:
void SerializeOut(HANDLE f)
{
fwrite(f, &Value1, sizeof(Value1), 1);
fwrite(f, &Value2, sizeof(Value2), 1);
int NameSize = strlen(Name);
fwrite(f, &NameSize, sizeof(NameSize), 1);
fwrite(f, Name, NameSize, 1);
}
void SerializeIn(HANDLE f)
{
...
}
};





This is better than doing a fwrite(Struct) since the later is not going to work on little/big-endian machines. Of course, you should encapsulate the HANDLE in a class that overload the << operator and only have a single Serialize function that both read and writes the data that handle the endianess of the target machine.

Share this post


Link to post
Share on other sites
they did provide a framework for the database and we have to hassle with their lean specification

the object they provide offers a cast operator which we use to get the data out of the object, I just wanted to get some backup before I tell the others not to use the sizeof operator

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement