Форум программистов, компьютерный форум, киберфорум
Наши страницы

Boost C++

Войти
Регистрация
Восстановить пароль
 
sl_k
12 / 12 / 0
Регистрация: 15.04.2010
Сообщений: 61
#1

boost serialization. Перегрузка save_construct_data и load_constract_data для шаблонных классов - Boost C++

10.04.2013, 22:17. Просмотров 970. Ответов 8
Метки нет (Все метки)

Добрый вечер,
снова сериализация и снова проблема.

Нужно сериализовать шаблонный класс без конструктора по умолчанию. Ниже приведен код, как я это делаю, но компилятор ругается
(classB выступает параметром для шаблона classA):

Bash
1
2
3
4
usr/include/boost/serialization/access.hpp:118:9: error: no matching function for call to ‘classA<classB>::serialize(boost::mpi::packed_iarchive&, const unsigned int&)’
 
/usr/include/boost/serialization/access.hpp:118:9: note: candidate is:
../myLib/include/mymath/referencevector.h:81:18: note: template<class Archive, class T1> void classA::serialize(Archive&, unsigned int) [with Archive = Archive, T1 = T1, T = classB]
вот вырезка из кода

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
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
template<typename T> classA; 
 
namespace boost {
     namespace serialization {
          template<class Archive,typename T1>
          void serialize(Archive & ar, const unsigned int version);
 
 
          template<class Archive, typename T1>
          inline void load_construct_data(Archive & ar, classA<T1> * t, const unsigned int file_version);
 
          template<class Archive, typename T1>
          inline void save_construct_data(Archive & ar, const classA<T1> * t, const unsigned int file_version);
 
    }
}
 
template<typename T> classA{
     public:
        classA(T* data): data_(data);
     private:
        T* data_;
 
        friend class boost::serialization::access;
        template<class Archive, typename T1> 
        void serialize(Archive & ar, const unsigned int version)
        {
        }
 
        template<class Archive, typename T1>
        friend void load_construct_data(Archive & ar, classA<T1>* t, const unsigned int file_version);
 
        template<class Archive, typename T1>
        friend void save_construct_data(Archive & ar, const class<T1>* t, const unsigned int file_version);
 
 
}
 
namespace boost {
    namespace serialization {
        template<class Archive, typename T1>
        inline void load_construct_data(Archive & ar, classA<T1>* t, const unsigned int file_version)
        {
             T1 data;
             ar >> data;
             ::new(t) classA<T1>(data);
        }
 
        template<class Archive, typename T1>
        inline void save_construct_data(Archive & ar, const classA<T1>* t, const unsigned int file_version)
        {
             ar << t.data_;
 
        }
 
 
 
 
   }
}
Хотелось бы знать, что еще нужно компилятору для полного счастья в этих функциях

Добавлено через 7 минут
Полное сообщение об ошибке:
Bash
1
2
3
4
5
6
7
8
9
10
11
12
13
14
/usr/include/boost/serialization/access.hpp: In static member function ‘static void    boost::serialization::access::serialize(Archive&, T&, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = classA<classB> >]’:
 
/usr/include/boost/serialization/serialization.hpp:69:5:   instantiated from ‘void boost::serialization::serialize(Archive&, T&, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = classA<classB> >]’
 
/usr/include/boost/serialization/serialization.hpp:128:9:   instantiated from ‘void boost::serialization::serialize_adl(Archive&, T&, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = classA<classB> >]’
 
/usr/include/boost/archive/detail/iserializer.hpp:188:5:   instantiated from ‘void boost::archive::detail::iserializer<Archive, T>::load_object_data(boost::archive::detail::basic_iarchive&, void*, unsigned int) const [with Archive = boost::mpi::packed_iarchive, T = classA<classB> >]’
 
./Main/main.cpp:391:1:   instantiated from here
 
usr/include/boost/serialization/access.hpp:118:9: error: no matching function for call to ‘classA<classB>::serialize(boost::mpi::packed_iarchive&, const unsigned int&)’
 
/usr/include/boost/serialization/access.hpp:118:9: note: candidate is:
../myLib/include/mymath/referencevector.h:81:18: note: template<class Archive, class T1> void classA::serialize(Archive&, unsigned int) [with Archive = Archive, T1 = T1, T = classB]
Добавлено через 46 минут
Проблема решилась, но возникла другая

допустим у нас classB тоже шаблонный, т. е.
C++
1
classB<T>
Код программы остается неизменным:
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
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
template<typename T> classA; 
 
namespace boost {
     namespace serialization {
 
          template<class Archive, typename T1>
          inline void load_construct_data(Archive & ar, classA<T1> * t, const unsigned int file_version);
 
          template<class Archive, typename T1>
          inline void save_construct_data(Archive & ar, const classA<T1> * t, const unsigned int file_version);
 
    }
}
 
template<typename T> classA{
     public:
        classA(T* data): data_(data);
     private:
        T* data_;
 
        friend class boost::serialization::access;
        template<class Archive> 
        void serialize(Archive & ar, const unsigned int version)
        {
        }
 
        template<class Archive, typename T1>
        friend void load_construct_data(Archive & ar, classA<T1>* t, const unsigned int file_version);
 
        template<class Archive, typename T1>
        friend void save_construct_data(Archive & ar, const class<T1>* t, const unsigned int file_version);
 
 
}
 
namespace boost {
    namespace serialization {
        template<class Archive, typename T1>
        inline void load_construct_data(Archive & ar, classA<T1>* t, const unsigned int file_version)
        {
             T1 data;
             ar >> data;
             ::new(t) classA<T1>(data);
        }
 
        template<class Archive, typename T1>
        inline void save_construct_data(Archive & ar, const classA<T1>* t, const unsigned int file_version)
        {
             ar << t.data_;
 
        }
 
 
 
 
   }
}

при компиляции вылетает ошибка:

Bash
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
/usr/include/boost/serialization/serialization.hpp: In function ‘void boost::serialization::load_construct_data_adl(Archive&, T*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = classA<classB<double> >]’:
 
/usr/include/boost/archive/detail/iserializer.hpp:319:9:   instantiated from ‘void boost::archive::detail::pointer_iserializer<Archive, T>::load_object_ptr(boost::archive::detail::basic_iarchive&, void*&, unsigned int) const [with Archive = boost::mpi::packed_iarchive, T = classA<classB<double> >]’
 
./main.cpp:391:1:   instantiated from here
 
/usr/include/boost/serialization/serialization.hpp:158:9: error: call of overloaded ‘load_construct_data(boost::mpi::packed_iarchive&, classA<classB<double> >*&, const boost::serialization::version_type&)’ is ambiguous
 
/usr/include/boost/serialization/serialization.hpp:158:9: note: candidates are:
 
/usr/include/boost/serialization/serialization.hpp:85:13: note: void boost::serialization::load_construct_data(Archive&, T*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = classA<classB<double> >]
 
../myClass.h: note: void myClass::load_construct_data(Archive&, classA<T1>*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T1 = classB<double>, T = double]
 
../myClass.h: note: void boost::serialization::load_construct_data(Archive&, classA<T1>*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T1 =classB<double>]
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
10.04.2013, 22:17
Здравствуйте! Я подобрал для вас темы с ответами на вопрос boost serialization. Перегрузка save_construct_data и load_constract_data для шаблонных классов (Boost C++):

boost::serialization - Boost C++
Нечто вроде ДБ написано с использованием boost::any (любой конечный элемент ДБ, то есть содержимое любой ячейки - объект Holder в котором...

boost::serialization - Boost C++
Хотел бы узнать, есть ли преимущество в записи файла с boost::serialization перед обычной записью?

boost::serialization - Boost C++
Рассматривал тему boost::serialization. И в примере ниже моя студия выкидывает много ошибок. Можете пожалуйста подсказать в чем бида ...

serialized via boost::serialization - Boost C++
Как можно считать информацию с файла в вектор, при этом не зная заранее его размерность. В фукнции save() я записываю в файл n человек, а...

Как подключить Boost::serialization в CMakeLists.txt? - Boost C++
Если кто-то работал с таким и готов помочь, то спасибо)

Boost::serialization, как сериализовать std::tuple? - Boost C++
В принципе вопрос в теме. Как именно?

8
ForEveR
В астрале
Эксперт С++
7985 / 4744 / 321
Регистрация: 24.06.2010
Сообщений: 10,547
Завершенные тесты: 3
11.04.2013, 09:44 #2
../myClass.h: note: void myClass::load_construct_data(Archive&, classA<T1>*, unsigned int) [with Archive = boost::mpi:acked_iarchive, T1 = classB<double>, T = double]

../myClass.h: note: void boost::serialization::load_construct_data(Archive&, classA<T1>*, unsigned int) [with Archive = boost::mpi:acked_iarchive, T1 =classB<double>]
Че-т как-то тут все указано ведь... У вас есть load_construct_data, save_construct_data в myClass?
1
sl_k
12 / 12 / 0
Регистрация: 15.04.2010
Сообщений: 61
11.04.2013, 13:45  [ТС] #3
ForEveR, да, именно там я их перегружал, но вылез еще один параметр Т непонятно откуда. (В смысле понятно, что из classB<T>, но этот класс - всего лишь один из вариантов)
C++
1
../myClass.h: note: void myClass::load_construct_data(Archive&, classA<T1>*, unsigned int) [with Archive = boost::mpi:acked_iarchive, T1 = classB<double>, T = double]
Кажется, многоуровневые шаблоны запутывают буст. Буду тогда, наверное, перегружать save_construct и load_construct для тех типов, которые мне нужны.
0
ForEveR
В астрале
Эксперт С++
7985 / 4744 / 321
Регистрация: 24.06.2010
Сообщений: 10,547
Завершенные тесты: 3
11.04.2013, 15:10 #4
sl_k,
Кажется, многоуровневые шаблоны запутывают буст.
Это буст всех запутывает многоуровневыми шаблонами, а не наоборот.) Честно говоря хотелось бы увидеть весь код, где возникает проблема, ибо тот кусок который вы скинули не дает никакого понимания.
1
sl_k
12 / 12 / 0
Регистрация: 15.04.2010
Сообщений: 61
11.04.2013, 15:29  [ТС] #5
ForEveR, да, может я намудрил в попытке упростить код. Вот оригинал:
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
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
namespace mymath {
    template<typename T> class ReferenceVector;
}
 
namespace boost {
    namespace serialization {
        template<class Archive, typename T1>
            inline void load_construct_data(Archive & ar, mymath::ReferenceVector<T1> * t, const unsigned int file_version);
        template<class Archive, typename T1>
            inline void save_construct_data(Archive & ar, const mymath::ReferenceVector<T1> * t, const unsigned int file_version);
 
    }
}
 
 
namespace mymath
{
 
  
    template<typename T> class ReferenceVector
    {
        public:
            ReferenceVector();
            ReferenceVector(const unsigned rows) throw (std::runtime_error);
            ReferenceVector(const unsigned rows, T * pdata);
            ~ReferenceVector();
            inline void resize(const unsigned rows) throw (std::runtime_error);
            inline void reshape(const unsigned rows, const T & pad) throw (std::runtime_error);
            inline ReferenceVector<T> * reference();
            inline void dereference();
            inline unsigned getRows() const;
            inline T * getData() const;
            inline void setName(std::string name);
            inline std::string getName() const;
            inline const T & operator()(const unsigned & row) const;
            inline T & operator()(const unsigned & row);
        private:
            unsigned rows_;
            unsigned reference_count_;
            bool user_mem_management_; // deallocation done by user
            T * data_;
            std::string name_;
            friend class boost::serialization::access;
            template<class Archive>
            void serialize(Archive & ar, const unsigned int version)
            {
            }
            // строка 82
            template<class Archive, typename T1>
                        friend void load_construct_data(Archive & ar, mymath::ReferenceVector<T1> * t, const unsigned int file_version);
 
            template<class Archive, typename T1>
                    friend void save_construct_data(Archive & ar, const mymath::ReferenceVector<T1> * t, const unsigned int file_version);
 
    };
namespace boost {
    namespace serialization {
        template<class Archive, typename T1>
                                        // строка 349
                    inline void load_construct_data(Archive & ar, mymath::ReferenceVector<T1>* t, const unsigned int file_version)
                    {
                        int nRows;
                        ar >> nRows;
 
                        ::new(t) mymath::ReferenceVector<T1>(nRows);
                        for (int iRow = 0; iRow < nRows; iRow++){
                            T1 data;
                            ar >> data;
                            t(iRow) = data;
                        }
 
                    }
 
             template<class Archive, typename T1>
                        inline void save_construct_data(Archive & ar, const mymath::ReferenceVector<T1> * t, const unsigned int file_version)
                                {
 
                                    // save data required to construct instance
                                    int nRows;
 
                                    nRows = t->getRows();
                                    ar << nRows;
 
                                    for (int iRow = 0; iRow < nRows; iRow++){
                                        ar << t(iRow);
 
                                    }
 
                                }
            }
        }
ну и ошибка:

Bash
1
2
3
4
5
6
7
8
/usr/include/boost/serialization/serialization.hpp: In function ‘void boost::serialization::load_construct_data_adl(Archive&, T*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = mymath::ReferenceVector<mymath::Matrix<double> >]’:
/usr/include/boost/archive/detail/iserializer.hpp:319:9:   instantiated from ‘void boost::archive::detail::pointer_iserializer<Archive, T>::load_object_ptr(boost::archive::detail::basic_iarchive&, void*&, unsigned int) const [with Archive = boost::mpi::packed_iarchive, T = mymath::ReferenceVector<mymath::Matrix<double> >]’
./Main/FaceList.cpp:391:1:   instantiated from here
/usr/include/boost/serialization/serialization.hpp:158:9: error: call of overloaded ‘load_construct_data(boost::mpi::packed_iarchive&, mymath::ReferenceVector<mymath::Matrix<double> >*&, const boost::serialization::version_type&)’ is ambiguous
/usr/include/boost/serialization/serialization.hpp:158:9: note: candidates are:
/usr/include/boost/serialization/serialization.hpp:85:13: note: void boost::serialization::load_construct_data(Archive&, T*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T = mymath::ReferenceVector<mymath::Matrix<double> >]
../myLib/include/mymath/referencevector.h:82:28: note: void mymath::load_construct_data(Archive&, mymath::ReferenceVector<T1>*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T1 = mymath::Matrix<double>, T = double]
../myLib/include/mymath/referencevector.h:349:18: note: void boost::serialization::load_construct_data(Archive&, mymath::ReferenceVector<T1>*, unsigned int) [with Archive = boost::mpi::packed_iarchive, T1 = mymath::Matrix<double>]
и такая же для save_construct_data
0
ForEveR
В астрале
Эксперт С++
7985 / 4744 / 321
Регистрация: 24.06.2010
Сообщений: 10,547
Завершенные тесты: 3
11.04.2013, 15:41 #6
sl_k, А где закрытие namespace mymath перед открытием namespace boost?
И впринципе это какая-то фиговая идея:

C++
1
2
template<class Archive, typename T1>
friend void load_construct_data(Archive & ar, mymath::ReferenceVector<T1> * t, const unsigned int file_version);
Функция ведь в namespace-е mymath, при этом форвард декларация в namespace-е boost::serialization...
1
sl_k
12 / 12 / 0
Регистрация: 15.04.2010
Сообщений: 61
11.04.2013, 16:11  [ТС] #7
ForEveR, пардон, оно там на месте, не стал копировать остальные функции класса, а там в конце скобка засела. не выделилось -> не скопировалось. но в этом плане все в порядке.

Добавлено через 20 минут
ForEveR, убрал из приватных эти функции. все закомпилировалось (еще пару маленьких ошибок пришлось подправить). Зачем я эти фунции туда поставил...? По-моему, вычитал на каком то ресурсе, что так делать надо. Они у меня во всех классах сидят и до этого компилятор не жаловался.
В любом случае, спасибо за помощь) Буду дальше мучать код бустом.
0
ForEveR
В астрале
Эксперт С++
7985 / 4744 / 321
Регистрация: 24.06.2010
Сообщений: 10,547
Завершенные тесты: 3
11.04.2013, 16:14 #8
sl_k, К слову, если прям так нужны friend-ы можно сделать
C++
1
2
3
4
   template<typename Archive, typename T1>
   friend void boost::serialization::load_construct_data(Archive&, C<T1>*, unsigned int);
   template<typename Archive, typename T1>
   friend void boost::serialization::save_construct_data(Archive&, const C<T1>*, unsigned int);
и все будет кошерно.

Лол. Я туплю. Тяжело читать такой шаблонный код, поэтому описку load_consruct_data вместо load_construct_data замечал долго...
1
sl_k
12 / 12 / 0
Регистрация: 15.04.2010
Сообщений: 61
11.04.2013, 17:16  [ТС] #9
ForEveR, действительно, приписав к френдам, что они из буста - и с френдами теперь тоже компилируется. Вот на таких заковыристых функциях и набирается опыт)

Добавлено через 6 минут
ps В остальных классах то у меня стоит что функции из boost::serialization
0
11.04.2013, 17:16
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
11.04.2013, 17:16
Привет! Вот еще темы с ответами:

boost::serialization. Как сериальзовывать собственные типы данных? - Boost C++
Как с помощью буста сериализовать следующий класс? class data{ private: std::string Name; std::string Type; unsigned...

boost serialization. загрузка данных из архива в std::list - Boost C++
День добрый, возникла небольшая проблема. Я сохраняю данные в архив используя #include&lt;boost/serialization/list.hpp&gt; ...

save_construct_data не хочет быть вызвана - Boost C++
Перегрузил функцию save_construct_data, но программа не хочет ее вызывать. namespace mymath { template&lt;typename T&gt; class...

Перегрузка шаблонных функций - C++
Есть сруктура box и два шаблоны для поиска максимального числа. Один для встроенных типов а второй для структуры. Если в функцию передается...


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

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.