Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > C/C++: Общие вопросы > проблемы с не-POD


Автор: GoldFinch 19.9.2009, 12:58
есть библиотека сериализации
в ней класс может быть сериализуем, 
если в нем есть метод serialize, который сериализует все поля класса
или тип класса "простой".

"простым" тип считается если он арифметический,
или если он наследуется от класса struct make_simple {/*empty*/};
или если для него специализирован шаблонный класс is_simple.

для сериализации простых типов используется memcpy

хотя классы, имеющие базовый класс, не считаются POD, классы вида
struct LoginFail : serialization::make_simple {...};
сериализуются нормально (конечно "неопределенное поведение", но удобно, т.к. работает)

я попробовал написать 
Код

#pragma pack(push,1)

template<int ID>
struct Packet
{
    typedef unsigned char id_t;
    
    static const id_t id = ID;

    template<class Archive>    void serialize(Archive & ar) {/*nothing*/}
};

struct LoginFail : Packet<0x01> , serialization::make_simple
{
    unsigned char reason;
};

и получил что
sizeof( LoginFail ) != 1
т.е. при наследовании от 2х пустых классов, тип уже не POD

я хотел бы в дальнейшем избежать этой ошибки, 
но проверка типов помеченных make_simple на то что они POD бесполезна, т.к. они по определению не POD
        // всегда failed
        BOOST_MPL_ASSERT(( 
            boost::mpl::if_< boost::is_base_of<make_simple,T>,
                boost::is_pod<T>, boost::mpl::true_ >
        )); 

можно ли как-то сделать проверку на то, можно ли копировать тип memcpy?

Автор: mes 19.9.2009, 22:12
 в суть пока не вникал, но на первый взгляд мне кажется тут подойдет решение сделать шаблон пакета "сквозным" :
Код

template<int ID, class Base>
struct Packet: Base {
...
struct LoginFail : Packet<0x01 , serialization::make_simple>
...

Автор: GoldFinch 19.9.2009, 23:24
действительно если избавиться от множественного наследования, лишние байты уберутся и sizeof будет как у POD

а проверку этой ошибки можно как нибудь сделать?

Автор: mes 20.9.2009, 00:10
компиляторо-зависимый способ: сравнить размер указателя на метод нужного класса.
другого не знаю.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)